Changes in / [73f6f12:2cde026d] in mod_gnutls


Ignore:
Files:
6 edited

Legend:

Unmodified
Added
Removed
  • README

    r73f6f12 r2cde026d  
    2222-------------
    2323
    24  * GnuTLS          >= 3.1.4 <http://www.gnutls.org/>
     24 * GnuTLS          >= 3.1.4 <http://www.gnutls.org/> (3.2.* or newer preferred)
    2525 * Apache HTTPD    >= 2.2 <http://httpd.apache.org/> (2.4.* preferred)
    2626 * autotools & gcc
  • docs/mod_gnutls_manual.mdwn

    r73f6f12 r2cde026d  
    367367as protection against statistical attacks to ciphertext data in order to
    368368achieve maximum compatibility (some broken mobile clients need this).
     369
     370`GnuTLSPIN`
     371------------------
     372
     373Set the PIN to be used to access encrypted key files or PKCS #11 objects.
     374
     375    GnuTLSPIN XXXXXX
     376
     377Default: *none*\
     378Context: server config, virtual host
     379
     380Takes a string to be used as a PIN for the protected objects in
     381a security module, or as a key to be used to decrypt PKCS #8, PKCS #12,
     382or openssl encrypted keys.
     383
     384`GnuTLSSRKPIN`
     385------------------
     386
     387Set the SRK PIN to be used to unlaccess the TPM.
     388
     389    GnuTLSSRKPIN XXXXXX
     390
     391Default: *none*\
     392Context: server config, virtual host
     393
     394Takes a string to be used as a PIN for the protected objects in
     395the TPM module.
    369396
    370397`GnuTLSExportCertificates`
  • include/mod_gnutls.h.in

    r73f6f12 r2cde026d  
    3434#include <gnutls/extra.h>
    3535#endif
     36#include <gnutls/abstract.h>
    3637#include <gnutls/openpgp.h>
    3738#include <gnutls/x509.h>
     
    104105/* Server Configuration Record */
    105106typedef struct {
     107    /* --- Configuration values --- */
     108        /* Is the module enabled? */
     109    int enabled;
     110        /* Is mod_proxy enabled? */
     111    int proxy_enabled;
     112        /* A Plain HTTP request */
     113    int non_ssl_request;
     114
     115    /* PIN used for PKCS #11 operations */
     116    char *pin;
     117
     118    /* the SRK PIN used in TPM operations */
     119    char *srk_pin;
     120
     121    char *x509_cert_file;
     122    char *x509_key_file;
     123    char *x509_ca_file;
     124
     125    char *pgp_cert_file;
     126    char *pgp_key_file;
     127    char *pgp_ring_file;
     128
     129    char *dh_file;
     130
     131    char *priorities_str;
     132
     133    const char* srp_tpasswd_file;
     134    const char* srp_tpasswd_conf_file;
     135
     136        /* Cache timeout value */
     137    int cache_timeout;
     138        /* Chose Cache Type */
     139    mgs_cache_e cache_type;
     140    const char* cache_config;
     141
     142        /* GnuTLS uses Session Tickets */
     143    int tickets;
     144
     145    /* --- Things initialized at _child_init --- */
     146
    106147    /* x509 Certificate Structure */
    107148    gnutls_certificate_credentials_t certs;
     
    126167    char* cert_cn;
    127168        /* Current x509 Certificate SAN [Subject Alternate Name]s*/
    128         char* cert_san[MAX_CERT_SAN];
    129         /* A x509 Certificate Chain */
    130     gnutls_x509_crt_t *certs_x509_chain;
    131         /* Current x509 Certificate Private Key */
    132     gnutls_x509_privkey_t privkey_x509;
    133         /* OpenPGP Certificate */
    134     gnutls_openpgp_crt_t cert_pgp;
    135         /* OpenPGP Certificate Private Key */
    136     gnutls_openpgp_privkey_t privkey_pgp;
     169    char* cert_san[MAX_CERT_SAN];
     170        /* An x509 Certificate Chain */
     171    gnutls_pcert_st *certs_x509_chain;
     172    gnutls_x509_crt_t *certs_x509_crt_chain;
    137173        /* Number of Certificates in Chain */
    138174    unsigned int certs_x509_chain_num;
    139         /* Is the module enabled? */
    140     int enabled;
     175
     176        /* Current x509 Certificate Private Key */
     177    gnutls_privkey_t privkey_x509;
     178
     179        /* OpenPGP Certificate */
     180    gnutls_pcert_st *cert_pgp;
     181    gnutls_openpgp_crt_t *cert_crt_pgp;
     182
     183        /* OpenPGP Certificate Private Key */
     184    gnutls_privkey_t privkey_pgp;
     185#if GNUTLS_VERSION_NUMBER < 0x030312
     186    /* Internal structure for the OpenPGP private key, used in the
     187     * workaround for a bug in gnutls_privkey_import_openpgp_raw that
     188     * frees memory that is still needed. DO NOT USE for any other
     189     * purpose. */
     190    gnutls_openpgp_privkey_t privkey_pgp_internal;
     191#endif
     192
    141193    /* Export full certificates to CGI environment: */
    142194    int export_certificates_size;
     
    145197        /* GnuTLS DH Parameters */
    146198    gnutls_dh_params_t dh_params;
    147         /* Cache timeout value */
    148     int cache_timeout;
    149         /* Chose Cache Type */
    150     mgs_cache_e cache_type;
    151     const char* cache_config;
    152     const char* srp_tpasswd_file;
    153     const char* srp_tpasswd_conf_file;
    154199        /* A list of CA Certificates */
    155200    gnutls_x509_crt_t *ca_list;
     
    164209        /* Last Cache timestamp */
    165210    apr_time_t last_cache_check;
    166         /* GnuTLS uses Session Tickets */
    167     int tickets;
    168         /* Is mod_proxy enabled? */
    169     int proxy_enabled;
    170         /* A Plain HTTP request */
    171     int non_ssl_request;
    172211} mgs_srvconf_rec;
    173212
     
    319358
    320359/**
     360 * Perform any reinitialization required in PKCS #11
     361 */
     362int mgs_pkcs11_reinit(server_rec * s);
     363
     364/**
    321365 * Convert a SSL Session ID into a Null Terminated Hex Encoded String
    322366 * @param id raw SSL Session ID
     
    338382
    339383/* Configuration Functions */
     384
     385/* Loads all files set in the configuration */
     386int mgs_load_files(apr_pool_t * p, server_rec * s);
    340387
    341388const char *mgs_set_srp_tpasswd_conf_file(cmd_parms * parms, void *dummy,
     
    371418const char *mgs_set_client_ca_file(cmd_parms * parms, void *dummy,
    372419                                   const char *arg);
     420const char *mgs_set_pin(cmd_parms * parms, void *dummy,
     421                                   const char *arg);
     422
     423const char *mgs_set_srk_pin(cmd_parms * parms, void *dummy,
     424                                   const char *arg);
    373425
    374426const char *mgs_set_keyring_file(cmd_parms * parms, void *dummy,
  • src/gnutls_config.c

    r73f6f12 r2cde026d  
    2020#include "mod_gnutls.h"
    2121#include "apr_lib.h"
     22#include <gnutls/abstract.h>
     23
     24#define INIT_CA_SIZE 128
    2225
    2326#ifdef APLOG_USE_MODULE
     
    2528#endif
    2629
     30static int pin_callback(void *user, int attempt __attribute__((unused)),
     31                        const char *token_url __attribute__((unused)),
     32                        const char *token_label, unsigned int flags,
     33                        char *pin, size_t pin_max)
     34{
     35    mgs_srvconf_rec *sc = user;
     36
     37    if (sc->pin == NULL || flags & GNUTLS_PIN_FINAL_TRY ||
     38        flags & GNUTLS_PIN_WRONG) {
     39        return -1;
     40    }
     41
     42    if (token_label && strcmp(token_label, "SRK") == 0) {
     43         snprintf(pin, pin_max, "%s", sc->srk_pin);
     44    } else {
     45         snprintf(pin, pin_max, "%s", sc->pin);
     46    }
     47    return 0;
     48}
     49
    2750static int load_datum_from_file(apr_pool_t * pool,
    28         const char *file, gnutls_datum_t * data) {
     51                                const char *file, gnutls_datum_t * data)
     52{
    2953    apr_file_t *fp;
    3054    apr_finfo_t finfo;
     
    3357
    3458    rv = apr_file_open(&fp, file, APR_READ | APR_BINARY,
    35             APR_OS_DEFAULT, pool);
     59                       APR_OS_DEFAULT, pool);
    3660    if (rv != APR_SUCCESS) {
    37         return rv;
     61        return rv;
    3862    }
    3963
     
    4165
    4266    if (rv != APR_SUCCESS) {
    43         return rv;
     67        return rv;
    4468    }
    4569
     
    4872
    4973    if (rv != APR_SUCCESS) {
    50         return rv;
     74        return rv;
    5175    }
    5276    apr_file_close(fp);
     
    5882}
    5983
     84/* 2048-bit group parameters from SRP specification */
     85const char static_dh_params[] = "-----BEGIN DH PARAMETERS-----\n"
     86        "MIIBBwKCAQCsa9tBMkqam/Fm3l4TiVgvr3K2ZRmH7gf8MZKUPbVgUKNzKcu0oJnt\n"
     87        "gZPgdXdnoT3VIxKrSwMxDc1/SKnaBP1Q6Ag5ae23Z7DPYJUXmhY6s2YaBfvV+qro\n"
     88        "KRipli8Lk7hV+XmT7Jde6qgNdArb9P90c1nQQdXDPqcdKB5EaxR3O8qXtDoj+4AW\n"
     89        "dr0gekNsZIHx0rkHhxdGGludMuaI+HdIVEUjtSSw1X1ep3onddLs+gMs+9v1L7N4\n"
     90        "YWAnkATleuavh05zA85TKZzMBBx7wwjYKlaY86jQw4JxrjX46dv7tpS1yAPYn3rk\n"
     91        "Nd4jbVJfVHWbZeNy/NaO8g+nER+eSv9zAgEC\n"
     92        "-----END DH PARAMETERS-----\n";
     93
     94int mgs_load_files(apr_pool_t * p, server_rec * s)
     95{
     96    apr_pool_t *spool;
     97    const char *file;
     98    gnutls_datum_t data;
     99    int ret;
     100    mgs_srvconf_rec *sc =
     101        (mgs_srvconf_rec *) ap_get_module_config(s->module_config,
     102                                                 &gnutls_module);
     103
     104    apr_pool_create(&spool, p);
     105
     106    sc->cert_pgp = apr_pcalloc(p, sizeof(sc->cert_pgp[0]));
     107    sc->cert_crt_pgp = apr_pcalloc(p, sizeof(sc->cert_crt_pgp[0]));
     108    sc->certs_x509_chain =
     109        apr_pcalloc(p, MAX_CHAIN_SIZE * sizeof(sc->certs_x509_chain[0]));
     110    sc->certs_x509_crt_chain =
     111        apr_pcalloc(p,
     112                    MAX_CHAIN_SIZE * sizeof(sc->certs_x509_crt_chain[0]));
     113
     114    ret = gnutls_certificate_allocate_credentials(&sc->certs);
     115    if (ret < 0) {
     116        ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     117                     "GnuTLS: Failed to initialize" ": (%d) %s", ret,
     118                     gnutls_strerror(ret));
     119        ret = -1;
     120        goto cleanup;
     121    }
     122
     123    ret = gnutls_anon_allocate_server_credentials(&sc->anon_creds);
     124    if (ret < 0) {
     125        ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     126                     "GnuTLS: Failed to initialize" ": (%d) %s", ret,
     127                     gnutls_strerror(ret));
     128        ret = -1;
     129        goto cleanup;
     130    }
     131
     132    /* Load SRP parameters */
     133#ifdef ENABLE_SRP
     134    ret = gnutls_srp_allocate_server_credentials(&sc->srp_creds);
     135    if (ret < 0) {
     136        ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     137                     "GnuTLS: Failed to initialize" ": (%d) %s", ret,
     138                     gnutls_strerror(ret));
     139        ret = -1;
     140        goto cleanup;
     141    }
     142
     143    if (sc->srp_tpasswd_conf_file != NULL && sc->srp_tpasswd_file != NULL) {
     144        ret = gnutls_srp_set_server_credentials_file
     145            (sc->srp_creds, sc->srp_tpasswd_file,
     146             sc->srp_tpasswd_conf_file);
     147
     148        if (ret < 0 && sc->enabled == GNUTLS_ENABLED_TRUE) {
     149            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0,
     150                         s,
     151                         "GnuTLS: Host '%s:%d' is missing a "
     152                         "SRP password or conf File!",
     153                         s->server_hostname, s->port);
     154            ret = -1;
     155            goto cleanup;
     156        }
     157    }
     158#endif
     159
     160    ret = gnutls_dh_params_init(&sc->dh_params);
     161    if (ret < 0) {
     162            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     163                         "GnuTLS: Failed to initialize"
     164                         ": (%d) %s", ret, gnutls_strerror(ret));
     165            ret = -1;
     166            goto cleanup;
     167    }
     168
     169    /* Load DH parameters */
     170    if (sc->dh_file) {
     171        if (load_datum_from_file(spool, sc->dh_file, &data) != 0) {
     172            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     173                         "GnuTLS: Error Reading " "DH params '%s'", sc->dh_file);
     174            ret = -1;
     175            goto cleanup;
     176        }
     177
     178        ret =
     179            gnutls_dh_params_import_pkcs3(sc->dh_params, &data,
     180                                          GNUTLS_X509_FMT_PEM);
     181        if (ret < 0) {
     182            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     183                         "GnuTLS: Failed to Import "
     184                         "DH params '%s': (%d) %s", sc->dh_file, ret,
     185                         gnutls_strerror(ret));
     186            ret = -1;
     187            goto cleanup;
     188        }
     189    } else {
     190        gnutls_datum_t pdata = {
     191            (void *) static_dh_params,
     192            sizeof(static_dh_params)
     193        };
     194
     195        ret = gnutls_dh_params_import_pkcs3(sc->dh_params, &pdata, GNUTLS_X509_FMT_PEM);
     196        if (ret < 0) {
     197            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     198                    "GnuTLS: Unable to generate or load DH Params: (%d) %s",
     199                    ret, gnutls_strerror(ret));
     200            ret = -1;
     201            goto cleanup;
     202        }
     203    }
     204
     205    if (sc->x509_cert_file != NULL) {
     206        unsigned int chain_num, i;
     207        unsigned format = GNUTLS_X509_FMT_PEM;
     208
     209        /* Load X.509 certificate */
     210        if (strncmp(sc->x509_cert_file, "pkcs11:", 7) == 0) {
     211            gnutls_pkcs11_obj_t obj;
     212
     213            file = sc->x509_cert_file;
     214
     215            ret = gnutls_pkcs11_obj_init(&obj);
     216            if (ret < 0) {
     217                ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     218                             "GnuTLS: Error Initializing PKCS #11 object");
     219                ret = -1;
     220                goto cleanup;
     221            }
     222
     223            gnutls_pkcs11_obj_set_pin_function(obj, pin_callback, sc);
     224
     225            ret = gnutls_pkcs11_obj_import_url(obj, file, GNUTLS_PKCS11_OBJ_FLAG_LOGIN);
     226            if (ret < 0) {
     227                ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     228                             "GnuTLS: Error Importing PKCS #11 object: '%s': %s",
     229                             file, gnutls_strerror(ret));
     230                ret = -1;
     231                goto cleanup;
     232            }
     233
     234            format = GNUTLS_X509_FMT_DER;
     235            ret = gnutls_pkcs11_obj_export2(obj, &data);
     236            if (ret < 0) {
     237                ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     238                             "GnuTLS: Error Exporting a PKCS #11 object: '%s': %s",
     239                             file, gnutls_strerror(ret));
     240                ret = -1;
     241                goto cleanup;
     242            }
     243
     244            gnutls_pkcs11_obj_deinit(obj);
     245        } else {
     246            file = ap_server_root_relative(spool, sc->x509_cert_file);
     247
     248            ret = gnutls_load_file(file, &data);
     249            if (ret < 0) {
     250                ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     251                             "GnuTLS: Error Reading Certificate '%s': %s",
     252                             file, gnutls_strerror(ret));
     253                ret = -1;
     254                goto cleanup;
     255            }
     256        }
     257
     258        ret =
     259            gnutls_x509_crt_list_import2(&sc->certs_x509_crt_chain,
     260                                        &chain_num, &data, format,
     261                                        GNUTLS_X509_CRT_LIST_FAIL_IF_UNSORTED);
     262        gnutls_free(data.data);
     263        sc->certs_x509_chain_num = chain_num;
     264
     265        if (ret < 0) {
     266            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     267                         "GnuTLS: Failed to Import Certificate Chain '%s': (%d) %s",
     268                         file, ret, gnutls_strerror(ret));
     269            ret = -1;
     270            goto cleanup;
     271        }
     272
     273        for (i = 0; i < chain_num; i++) {
     274            ret =
     275                gnutls_pcert_import_x509(&sc->certs_x509_chain[i],
     276                                         sc->certs_x509_crt_chain[i], 0);
     277            if (ret < 0) {
     278                ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     279                             "GnuTLS: Failed to Import pCertificate '%s': (%d) %s",
     280                             file, ret, gnutls_strerror(ret));
     281                ret = -1;
     282                goto cleanup;
     283            }
     284        }
     285        sc->certs_x509_chain_num = chain_num;
     286    }
     287
     288    if (sc->x509_key_file) {
     289        ret = gnutls_privkey_init(&sc->privkey_x509);
     290        if (ret < 0) {
     291            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     292                         "GnuTLS: Failed to initialize: (%d) %s", ret,
     293                         gnutls_strerror(ret));
     294            ret = -1;
     295            goto cleanup;
     296        }
     297
     298        if (gnutls_url_is_supported(sc->x509_key_file) != 0) {
     299            file = sc->x509_key_file;
     300
     301            gnutls_privkey_set_pin_function(sc->privkey_x509, pin_callback,
     302                                            sc);
     303
     304            ret = gnutls_privkey_import_url(sc->privkey_x509, file, 0);
     305
     306            if (ret < 0) {
     307                ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     308                             "GnuTLS: Failed to Import Private Key URL '%s': (%d) %s",
     309                             file, ret, gnutls_strerror(ret));
     310                ret = -1;
     311                goto cleanup;
     312            }
     313        } else {
     314            file = ap_server_root_relative(spool, sc->x509_key_file);
     315
     316            if (load_datum_from_file(spool, file, &data) != 0) {
     317                ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     318                             "GnuTLS: Error Reading Private Key '%s'",
     319                             file);
     320                ret = -1;
     321                goto cleanup;
     322            }
     323
     324            ret =
     325                gnutls_privkey_import_x509_raw(sc->privkey_x509, &data,
     326                                               GNUTLS_X509_FMT_PEM, sc->pin,
     327                                               0);
     328
     329            if (ret < 0) {
     330                ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     331                             "GnuTLS: Failed to Import Private Key '%s': (%d) %s",
     332                             file, ret, gnutls_strerror(ret));
     333                ret = -1;
     334                goto cleanup;
     335            }
     336        }
     337    }
     338
     339    /* Load the X.509 CA file */
     340    if (sc->x509_ca_file) {
     341        if (load_datum_from_file(spool, sc->x509_ca_file, &data) != 0) {
     342            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     343                         "GnuTLS: Error Reading " "Client CA File '%s'",
     344                         sc->x509_ca_file);
     345            ret = -1;
     346            goto cleanup;
     347        }
     348
     349        ret = gnutls_x509_crt_list_import2(&sc->ca_list, &sc->ca_list_size,
     350                                         &data, GNUTLS_X509_FMT_PEM, 0);
     351        if (ret < 0) {
     352            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     353                         "GnuTLS: Failed to load "
     354                         "Client CA File '%s': (%d) %s", sc->x509_ca_file,
     355                         ret, gnutls_strerror(ret));
     356            ret = -1;
     357            goto cleanup;
     358        }
     359    }
     360
     361    if (sc->pgp_cert_file) {
     362        if (load_datum_from_file(spool, sc->pgp_cert_file, &data) != 0) {
     363            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     364                         "GnuTLS: Error Reading " "Certificate '%s'",
     365                         sc->pgp_cert_file);
     366            ret = -1;
     367            goto cleanup;
     368        }
     369
     370        ret = gnutls_openpgp_crt_init(&sc->cert_crt_pgp[0]);
     371        if (ret < 0) {
     372            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     373                         "GnuTLS: Failed to Init "
     374                         "PGP Certificate: (%d) %s", ret,
     375                         gnutls_strerror(ret));
     376            ret = -1;
     377            goto cleanup;
     378        }
     379
     380        ret =
     381            gnutls_openpgp_crt_import(sc->cert_crt_pgp[0], &data,
     382                                      GNUTLS_OPENPGP_FMT_BASE64);
     383        if (ret < 0) {
     384            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     385                         "GnuTLS: Failed to Import "
     386                         "PGP Certificate: (%d) %s", ret,
     387                         gnutls_strerror(ret));
     388            ret = -1;
     389            goto cleanup;
     390        }
     391
     392        ret =
     393            gnutls_pcert_import_openpgp(sc->cert_pgp, sc->cert_crt_pgp[0],
     394                                        0);
     395        if (ret < 0) {
     396            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     397                         "GnuTLS: Failed to Import "
     398                         "PGP pCertificate: (%d) %s", ret,
     399                         gnutls_strerror(ret));
     400            ret = -1;
     401            goto cleanup;
     402        }
     403    }
     404
     405    /* Load the PGP key file */
     406    if (sc->pgp_key_file) {
     407        if (load_datum_from_file(spool, sc->pgp_key_file, &data) != 0) {
     408            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     409                         "GnuTLS: Error Reading " "Private Key '%s'",
     410                         sc->pgp_key_file);
     411            ret = -1;
     412            goto cleanup;
     413        }
     414
     415        ret = gnutls_privkey_init(&sc->privkey_pgp);
     416        if (ret < 0) {
     417            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     418                         "GnuTLS: Failed to initialize"
     419                         ": (%d) %s", ret, gnutls_strerror(ret));
     420            ret = -1;
     421            goto cleanup;
     422        }
     423
     424#if GNUTLS_VERSION_NUMBER < 0x030312
     425        /* GnuTLS versions before 3.3.12 contain a bug in
     426         * gnutls_privkey_import_openpgp_raw which frees data that is
     427         * accessed when the key is used, leading to segfault. Loading
     428         * the key into a gnutls_openpgp_privkey_t and then assigning
     429         * it to the gnutls_privkey_t works around the bug, hence this
     430         * chain of gnutls_openpgp_privkey_init,
     431         * gnutls_openpgp_privkey_import and
     432         * gnutls_privkey_import_openpgp. */
     433        ret = gnutls_openpgp_privkey_init(&sc->privkey_pgp_internal);
     434        if (ret != 0) {
     435            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     436                         "GnuTLS: Failed to initialize "
     437                         "PGP Private Key '%s': (%d) %s",
     438                         sc->pgp_key_file, ret, gnutls_strerror(ret));
     439            ret = -1;
     440            goto cleanup;
     441        }
     442
     443        ret = gnutls_openpgp_privkey_import(sc->privkey_pgp_internal, &data,
     444                                            GNUTLS_OPENPGP_FMT_BASE64, NULL, 0);
     445        if (ret != 0) {
     446            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     447                         "GnuTLS: Failed to Import "
     448                         "PGP Private Key '%s': (%d) %s",
     449                         sc->pgp_key_file, ret, gnutls_strerror(ret));
     450            ret = -1;
     451            goto cleanup;
     452        }
     453
     454        ret = gnutls_privkey_import_openpgp(sc->privkey_pgp,
     455                                            sc->privkey_pgp_internal, 0);
     456        if (ret != 0)
     457        {
     458            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     459                         "GnuTLS: Failed to assign PGP Private Key '%s' "
     460                         "to gnutls_privkey_t structure: (%d) %s",
     461                         sc->pgp_key_file, ret, gnutls_strerror(ret));
     462            ret = -1;
     463            goto cleanup;
     464        }
     465#else
     466        ret = gnutls_privkey_import_openpgp_raw(sc->privkey_pgp, &data,
     467                                                GNUTLS_OPENPGP_FMT_BASE64,
     468                                                NULL, NULL);
     469        if (ret != 0)
     470        {
     471            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     472                         "GnuTLS: Failed to Import "
     473                         "PGP Private Key '%s': (%d) %s",
     474                         sc->pgp_key_file, ret, gnutls_strerror(ret));
     475            ret = -1;
     476            goto cleanup;
     477        }
     478#endif
     479    }
     480
     481    /* Load the keyring file */
     482    if (sc->pgp_ring_file) {
     483        if (load_datum_from_file(spool, sc->pgp_ring_file, &data) != 0) {
     484            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     485                         "GnuTLS: Error Reading " "Keyring File '%s'",
     486                         sc->pgp_ring_file);
     487            ret = -1;
     488            goto cleanup;
     489        }
     490
     491        ret = gnutls_openpgp_keyring_init(&sc->pgp_list);
     492        if (ret < 0) {
     493            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     494                         "GnuTLS: Failed to initialize"
     495                         "keyring: (%d) %s", ret, gnutls_strerror(ret));
     496            ret = -1;
     497            goto cleanup;
     498        }
     499
     500        ret = gnutls_openpgp_keyring_import(sc->pgp_list, &data,
     501                                           GNUTLS_OPENPGP_FMT_BASE64);
     502        if (ret < 0) {
     503            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     504                         "GnuTLS: Failed to load "
     505                         "Keyring File '%s': (%d) %s", sc->pgp_ring_file,
     506                         ret, gnutls_strerror(ret));
     507            ret = -1;
     508            goto cleanup;
     509        }
     510    }
     511
     512    if (sc->priorities_str) {
     513        const char *err;
     514        ret = gnutls_priority_init(&sc->priorities, sc->priorities_str, &err);
     515
     516        if (ret < 0) {
     517            if (ret == GNUTLS_E_INVALID_REQUEST) {
     518                ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     519                             "GnuTLS: Syntax error parsing priorities string at: %s",
     520                             err);
     521            } else {
     522                ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     523                             "GnuTLS: error parsing priorities string");
     524
     525            }
     526            ret = -1;
     527            goto cleanup;
     528        }
     529    }
     530
     531    ret = 0;
     532  cleanup:
     533    apr_pool_destroy(spool);
     534
     535    return ret;
     536}
     537
     538int mgs_pkcs11_reinit(server_rec * base_server)
     539{
     540    int ret;
     541    server_rec *s;
     542    mgs_srvconf_rec *sc;
     543
     544    gnutls_pkcs11_reinit();
     545
     546    for (s = base_server; s; s = s->next) {
     547        sc = (mgs_srvconf_rec *) ap_get_module_config(s->module_config, &gnutls_module);
     548
     549            /* gnutls caches the session in a private key, so we need to open
     550             * a new one */
     551            if (sc->x509_key_file && gnutls_url_is_supported(sc->x509_key_file) != 0) {
     552                gnutls_privkey_deinit(sc->privkey_x509);
     553
     554                ret = gnutls_privkey_init(&sc->privkey_x509);
     555                if (ret < 0) {
     556                    ap_log_error(APLOG_MARK, APLOG_EMERG, 0, s,
     557                                 "GnuTLS: Failed to initialize: (%d) %s", ret,
     558                                 gnutls_strerror(ret));
     559                    goto fail;
     560                }
     561
     562                gnutls_privkey_set_pin_function(sc->privkey_x509, pin_callback, sc);
     563
     564                ret = gnutls_privkey_import_url(sc->privkey_x509, sc->x509_key_file, 0);
     565                if (ret < 0) {
     566                    ap_log_error(APLOG_MARK, APLOG_EMERG, 0, s,
     567                             "GnuTLS: Failed to Re-Import Private Key URL '%s': (%d) %s",
     568                             sc->x509_key_file, ret, gnutls_strerror(ret));
     569                    goto fail;
     570                }
     571            }
     572    }
     573
     574    return 0;
     575
     576 fail:
     577    gnutls_privkey_deinit(sc->privkey_x509);
     578    return -1;
     579}
     580
    60581const char *mgs_set_dh_file(cmd_parms * parms, void *dummy __attribute__((unused)),
    61582        const char *arg) {
    62     int ret;
    63     gnutls_datum_t data;
    64     const char *file;
    65     apr_pool_t *spool;
    66     mgs_srvconf_rec *sc =
    67             (mgs_srvconf_rec *) ap_get_module_config(parms->server->
    68             module_config,
    69             &gnutls_module);
    70 
    71     apr_pool_create(&spool, parms->pool);
    72 
    73     file = ap_server_root_relative(spool, arg);
    74 
    75     if (load_datum_from_file(spool, file, &data) != 0) {
    76         return apr_psprintf(parms->pool, "GnuTLS: Error Reading "
    77                 "DH params '%s'", file);
    78     }
    79 
    80     ret = gnutls_dh_params_init(&sc->dh_params);
    81     if (ret < 0) {
    82         return apr_psprintf(parms->pool,
    83                 "GnuTLS: Failed to initialize"
    84                 ": (%d) %s", ret,
    85                 gnutls_strerror(ret));
    86     }
    87 
    88     ret =
    89             gnutls_dh_params_import_pkcs3(sc->dh_params, &data,
    90             GNUTLS_X509_FMT_PEM);
    91     if (ret < 0) {
    92         return apr_psprintf(parms->pool,
    93                 "GnuTLS: Failed to Import "
    94                 "DH params '%s': (%d) %s", file, ret,
    95                 gnutls_strerror(ret));
    96     }
    97 
    98     apr_pool_destroy(spool);
    99 
    100     return NULL;
    101 }
    102 
    103 const char *mgs_set_cert_file(cmd_parms * parms, void *dummy __attribute__((unused)), const char *arg)
     583    mgs_srvconf_rec *sc =
     584        (mgs_srvconf_rec *) ap_get_module_config(parms->server->
     585                                                 module_config,
     586                                                 &gnutls_module);
     587
     588    sc->dh_file = ap_server_root_relative(parms->pool, arg);
     589
     590    return NULL;
     591}
     592
     593const char *mgs_set_cert_file(cmd_parms * parms, void *dummy __attribute__((unused)), const char *arg) {
     594
     595    mgs_srvconf_rec *sc =
     596        (mgs_srvconf_rec *) ap_get_module_config(parms->
     597                                                 server->module_config,
     598                                                 &gnutls_module);
     599
     600    sc->x509_cert_file = apr_pstrdup(parms->pool, arg);
     601
     602    return NULL;
     603
     604}
     605
     606const char *mgs_set_key_file(cmd_parms * parms, void *dummy __attribute__((unused)), const char *arg) {
     607
     608    mgs_srvconf_rec *sc =
     609        (mgs_srvconf_rec *) ap_get_module_config(parms->
     610                                                 server->module_config,
     611                                                 &gnutls_module);
     612
     613    sc->x509_key_file = apr_pstrdup(parms->pool, arg);
     614
     615    return NULL;
     616}
     617
     618const char *mgs_set_pgpcert_file(cmd_parms * parms, void *dummy __attribute__((unused)),
     619        const char *arg)
    104620{
    105     int ret;
    106     gnutls_datum_t data;
    107     const char *file;
    108     apr_pool_t *spool;
    109 
    110     mgs_srvconf_rec *sc = (mgs_srvconf_rec *) ap_get_module_config(parms->server->module_config, &gnutls_module);
    111     apr_pool_create(&spool, parms->pool);
    112 
    113     file = ap_server_root_relative(spool, arg);
    114 
    115     if (load_datum_from_file(spool, file, &data) != 0) {
    116                 apr_pool_destroy(spool);
    117         return apr_psprintf(parms->pool, "GnuTLS: Error Reading Certificate '%s'", file);
    118     }
    119 
    120     sc->certs_x509_chain_num = MAX_CHAIN_SIZE;
    121     ret = gnutls_x509_crt_list_import(sc->certs_x509_chain, &sc->certs_x509_chain_num, &data, GNUTLS_X509_FMT_PEM, 0);
    122     if (ret < 0) {
    123                 apr_pool_destroy(spool);
    124         return apr_psprintf(parms->pool, "GnuTLS: Failed to Import Certificate '%s': (%d) %s", file, ret, gnutls_strerror(ret));
    125     }
    126 
    127         apr_pool_destroy(spool);
    128     return NULL;
    129 
    130 }
    131 
    132 const char *mgs_set_key_file(cmd_parms * parms, void *dummy __attribute__((unused)), const char *arg) {
    133 
    134     int ret;
    135     gnutls_datum_t data;
    136     const char *file;
    137     apr_pool_t *spool;
    138     const char *out;
    139 
    140         mgs_srvconf_rec *sc = (mgs_srvconf_rec *) ap_get_module_config(parms->server->module_config, &gnutls_module);
    141 
    142         apr_pool_create(&spool, parms->pool);
    143 
    144     file = ap_server_root_relative(spool, arg);
    145 
    146     if (load_datum_from_file(spool, file, &data) != 0) {
    147         out = apr_psprintf(parms->pool, "GnuTLS: Error Reading Private Key '%s'", file);
    148                 apr_pool_destroy(spool);
    149         return out;
    150     }
    151 
    152     ret = gnutls_x509_privkey_init(&sc->privkey_x509);
    153 
    154     if (ret < 0) {
    155                 apr_pool_destroy(spool);
    156         return apr_psprintf(parms->pool, "GnuTLS: Failed to initialize: (%d) %s", ret, gnutls_strerror(ret));
    157     }
    158 
    159     ret = gnutls_x509_privkey_import(sc->privkey_x509, &data, GNUTLS_X509_FMT_PEM);
    160 
    161     if (ret < 0) {
    162         ret = gnutls_x509_privkey_import_pkcs8(sc->privkey_x509, &data, GNUTLS_X509_FMT_PEM, NULL, GNUTLS_PKCS_PLAIN);
    163         }
    164 
    165     if (ret < 0) {
    166         out = apr_psprintf(parms->pool, "GnuTLS: Failed to Import Private Key '%s': (%d) %s", file, ret, gnutls_strerror(ret));
    167                 apr_pool_destroy(spool);
    168         return out;
    169     }
    170 
    171     apr_pool_destroy(spool);
    172 
    173     return NULL;
    174 }
    175 
    176 const char *mgs_set_pgpcert_file(cmd_parms * parms, void *dummy __attribute__((unused)),
    177         const char *arg) {
    178     int ret;
    179     gnutls_datum_t data;
    180     const char *file;
    181     apr_pool_t *spool;
    182     mgs_srvconf_rec *sc =
    183             (mgs_srvconf_rec *) ap_get_module_config(parms->server->
    184             module_config,
    185             &gnutls_module);
    186     apr_pool_create(&spool, parms->pool);
    187 
    188     file = ap_server_root_relative(spool, arg);
    189 
    190     if (load_datum_from_file(spool, file, &data) != 0) {
    191         return apr_psprintf(parms->pool, "GnuTLS: Error Reading "
    192                 "Certificate '%s'", file);
    193     }
    194 
    195     ret = gnutls_openpgp_crt_init(&sc->cert_pgp);
    196     if (ret < 0) {
    197         return apr_psprintf(parms->pool, "GnuTLS: Failed to Init "
    198                 "PGP Certificate: (%d) %s", ret,
    199                 gnutls_strerror(ret));
    200     }
    201 
    202     ret =
    203             gnutls_openpgp_crt_import(sc->cert_pgp, &data,
    204             GNUTLS_OPENPGP_FMT_BASE64);
    205     if (ret < 0) {
    206         return apr_psprintf(parms->pool,
    207                 "GnuTLS: Failed to Import "
    208                 "PGP Certificate '%s': (%d) %s", file,
    209                 ret, gnutls_strerror(ret));
    210     }
    211 
    212     apr_pool_destroy(spool);
     621    mgs_srvconf_rec *sc =
     622        (mgs_srvconf_rec *) ap_get_module_config(parms->server->
     623                                                 module_config,
     624                                                 &gnutls_module);
     625
     626    sc->pgp_cert_file = ap_server_root_relative(parms->pool, arg);
     627
    213628    return NULL;
    214629}
     
    216631const char *mgs_set_pgpkey_file(cmd_parms * parms, void *dummy __attribute__((unused)),
    217632        const char *arg) {
    218     int ret;
    219     gnutls_datum_t data;
    220     const char *file;
    221     apr_pool_t *spool;
    222     mgs_srvconf_rec *sc =
    223             (mgs_srvconf_rec *) ap_get_module_config(parms->server->
    224             module_config,
    225             &gnutls_module);
    226     apr_pool_create(&spool, parms->pool);
    227 
    228     file = ap_server_root_relative(spool, arg);
    229 
    230     if (load_datum_from_file(spool, file, &data) != 0) {
    231         return apr_psprintf(parms->pool, "GnuTLS: Error Reading "
    232                 "Private Key '%s'", file);
    233     }
    234 
    235     ret = gnutls_openpgp_privkey_init(&sc->privkey_pgp);
    236     if (ret < 0) {
    237         return apr_psprintf(parms->pool,
    238                 "GnuTLS: Failed to initialize"
    239                 ": (%d) %s", ret,
    240                 gnutls_strerror(ret));
    241     }
    242 
    243     ret =
    244             gnutls_openpgp_privkey_import(sc->privkey_pgp, &data,
    245             GNUTLS_OPENPGP_FMT_BASE64, NULL,
    246             0);
    247     if (ret != 0) {
    248         return apr_psprintf(parms->pool,
    249                 "GnuTLS: Failed to Import "
    250                 "PGP Private Key '%s': (%d) %s", file,
    251                 ret, gnutls_strerror(ret));
    252     }
    253     apr_pool_destroy(spool);
     633    mgs_srvconf_rec *sc =
     634        (mgs_srvconf_rec *) ap_get_module_config(parms->server->
     635                                                 module_config,
     636                                                 &gnutls_module);
     637
     638    sc->pgp_key_file = ap_server_root_relative(parms->pool, arg);
     639
    254640    return NULL;
    255641}
     
    258644        const char *arg) {
    259645    mgs_srvconf_rec *sc =
    260             (mgs_srvconf_rec *) ap_get_module_config(parms->server->
    261             module_config,
    262             &gnutls_module);
     646        (mgs_srvconf_rec *) ap_get_module_config(parms->server->
     647                                                module_config,
     648                                                &gnutls_module);
    263649
    264650    sc->tickets = 0;
    265651    if (strcasecmp("on", arg) == 0) {
    266         sc->tickets = 1;
     652        sc->tickets = 1;
    267653    }
    268654
     
    276662        const char *arg) {
    277663    mgs_srvconf_rec *sc =
    278             (mgs_srvconf_rec *) ap_get_module_config(parms->server->
    279             module_config,
    280             &gnutls_module);
     664        (mgs_srvconf_rec *) ap_get_module_config(parms->server->
     665                                                module_config,
     666                                                &gnutls_module);
    281667
    282668    sc->srp_tpasswd_file = ap_server_root_relative(parms->pool, arg);
     
    288674        const char *arg) {
    289675    mgs_srvconf_rec *sc =
    290             (mgs_srvconf_rec *) ap_get_module_config(parms->server->
    291             module_config,
    292             &gnutls_module);
    293 
    294     sc->srp_tpasswd_conf_file =
    295             ap_server_root_relative(parms->pool, arg);
     676        (mgs_srvconf_rec *) ap_get_module_config(parms->server->
     677                                                 module_config,
     678                                                 &gnutls_module);
     679
     680    sc->srp_tpasswd_conf_file = ap_server_root_relative(parms->pool, arg);
    296681
    297682    return NULL;
     
    304689    const char *err;
    305690    mgs_srvconf_rec *sc =
    306             ap_get_module_config(parms->server->module_config,
    307             &gnutls_module);
     691        ap_get_module_config(parms->server->module_config,
     692                             &gnutls_module);
    308693    if ((err = ap_check_cmd_context(parms, GLOBAL_ONLY))) {
    309         return err;
     694        return err;
    310695    }
    311696
    312697    if (strcasecmp("none", type) == 0) {
    313         sc->cache_type = mgs_cache_none;
    314         sc->cache_config = NULL;
    315         return NULL;
     698        sc->cache_type = mgs_cache_none;
     699        sc->cache_config = NULL;
     700        return NULL;
    316701    } else if (strcasecmp("dbm", type) == 0) {
    317         sc->cache_type = mgs_cache_dbm;
     702        sc->cache_type = mgs_cache_dbm;
    318703    } else if (strcasecmp("gdbm", type) == 0) {
    319         sc->cache_type = mgs_cache_gdbm;
     704        sc->cache_type = mgs_cache_gdbm;
    320705    }
    321706#if HAVE_APR_MEMCACHE
    322707    else if (strcasecmp("memcache", type) == 0) {
    323         sc->cache_type = mgs_cache_memcache;
     708        sc->cache_type = mgs_cache_memcache;
    324709    }
    325710#endif
    326711    else {
    327         return "Invalid Type for GnuTLSCache!";
     712        return "Invalid Type for GnuTLSCache!";
    328713    }
    329714
    330715    if (arg == NULL)
    331         return "Invalid argument 2 for GnuTLSCache!";
     716        return "Invalid argument 2 for GnuTLSCache!";
    332717
    333718    if (sc->cache_type == mgs_cache_dbm
    334             || sc->cache_type == mgs_cache_gdbm) {
    335         sc->cache_config =
    336                 ap_server_root_relative(parms->pool, arg);
     719        || sc->cache_type == mgs_cache_gdbm) {
     720        sc->cache_config = ap_server_root_relative(parms->pool, arg);
    337721    } else {
    338         sc->cache_config = apr_pstrdup(parms->pool, arg);
     722        sc->cache_config = apr_pstrdup(parms->pool, arg);
    339723    }
    340724
     
    347731    const char *err;
    348732    mgs_srvconf_rec *sc =
    349             (mgs_srvconf_rec *) ap_get_module_config(parms->server->
    350             module_config,
    351             &gnutls_module);
     733        (mgs_srvconf_rec *) ap_get_module_config(parms->server->
     734                                                module_config,
     735                                                &gnutls_module);
    352736
    353737    if ((err = ap_check_cmd_context(parms, GLOBAL_ONLY))) {
    354         return err;
     738        return err;
    355739    }
    356740
     
    358742
    359743    if (argint < 0) {
    360         return "GnuTLSCacheTimeout: Invalid argument";
     744        return "GnuTLSCacheTimeout: Invalid argument";
    361745    } else if (argint == 0) {
    362         sc->cache_timeout = 0;
     746        sc->cache_timeout = 0;
    363747    } else {
    364         sc->cache_timeout = apr_time_from_sec(argint);
     748        sc->cache_timeout = apr_time_from_sec(argint);
    365749    }
    366750
     
    373757
    374758    if (strcasecmp("cartel", arg) == 0) {
    375         sc->client_verify_method = mgs_cvm_cartel;
     759        sc->client_verify_method = mgs_cvm_cartel;
    376760    } else if (strcasecmp("msva", arg) == 0) {
    377761#ifdef ENABLE_MSVA
    378         sc->client_verify_method = mgs_cvm_msva;
     762        sc->client_verify_method = mgs_cvm_msva;
    379763#else
    380         return "GnuTLSClientVerifyMethod: msva is not supported";
     764        return "GnuTLSClientVerifyMethod: msva is not supported";
    381765#endif
    382766    } else {
    383         return "GnuTLSClientVerifyMethod: Invalid argument";
     767        return "GnuTLSClientVerifyMethod: Invalid argument";
    384768    }
    385769
     
    393777
    394778    if (strcasecmp("none", arg) == 0 || strcasecmp("ignore", arg) == 0) {
    395         mode = GNUTLS_CERT_IGNORE;
     779        mode = GNUTLS_CERT_IGNORE;
    396780    } else if (strcasecmp("optional", arg) == 0
    397             || strcasecmp("request", arg) == 0) {
    398         mode = GNUTLS_CERT_REQUEST;
     781               || strcasecmp("request", arg) == 0) {
     782        mode = GNUTLS_CERT_REQUEST;
    399783    } else if (strcasecmp("require", arg) == 0) {
    400         mode = GNUTLS_CERT_REQUIRE;
     784        mode = GNUTLS_CERT_REQUIRE;
    401785    } else {
    402         return "GnuTLSClientVerify: Invalid argument";
     786        return "GnuTLSClientVerify: Invalid argument";
    403787    }
    404788
     
    408792        dc->client_verify_mode = mode;
    409793    } else {
    410         mgs_srvconf_rec *sc =
    411                 (mgs_srvconf_rec *)
    412                 ap_get_module_config(parms->server->module_config,
    413                 &gnutls_module);
    414         sc->client_verify_mode = mode;
    415     }
    416 
    417     return NULL;
    418 }
    419 
    420 #define INIT_CA_SIZE 128
     794        mgs_srvconf_rec *sc = (mgs_srvconf_rec *)
     795            ap_get_module_config(parms->server->module_config,
     796                                 &gnutls_module);
     797        sc->client_verify_mode = mode;
     798    }
     799
     800    return NULL;
     801}
    421802
    422803const char *mgs_set_client_ca_file(cmd_parms * parms, void *dummy __attribute__((unused)),
    423804        const char *arg) {
    424     int rv;
    425     const char *file;
    426     apr_pool_t *spool;
    427     gnutls_datum_t data;
    428 
    429     mgs_srvconf_rec *sc =
    430             (mgs_srvconf_rec *) ap_get_module_config(parms->server->
    431             module_config,
    432             &gnutls_module);
    433     apr_pool_create(&spool, parms->pool);
    434 
    435     file = ap_server_root_relative(spool, arg);
    436 
    437     if (load_datum_from_file(spool, file, &data) != 0) {
    438         return apr_psprintf(parms->pool, "GnuTLS: Error Reading "
    439                 "Client CA File '%s'", file);
    440     }
    441 
    442     sc->ca_list_size = INIT_CA_SIZE;
    443     sc->ca_list = malloc(sc->ca_list_size * sizeof (*sc->ca_list));
    444     if (sc->ca_list == NULL) {
    445         return apr_psprintf(parms->pool,
    446                 "mod_gnutls: Memory allocation error");
    447     }
    448 
    449     rv = gnutls_x509_crt_list_import(sc->ca_list, &sc->ca_list_size,
    450             &data, GNUTLS_X509_FMT_PEM,
    451             GNUTLS_X509_CRT_LIST_IMPORT_FAIL_IF_EXCEED);
    452     if (rv < 0 && rv != GNUTLS_E_SHORT_MEMORY_BUFFER) {
    453         return apr_psprintf(parms->pool, "GnuTLS: Failed to load "
    454                 "Client CA File '%s': (%d) %s", file,
    455                 rv, gnutls_strerror(rv));
    456     }
    457 
    458     if (INIT_CA_SIZE < sc->ca_list_size) {
    459         sc->ca_list =
    460                 realloc(sc->ca_list,
    461                 sc->ca_list_size * sizeof (*sc->ca_list));
    462         if (sc->ca_list == NULL) {
    463             return apr_psprintf(parms->pool,
    464                     "mod_gnutls: Memory allocation error");
    465         }
    466 
    467         /* re-read */
    468         rv = gnutls_x509_crt_list_import(sc->ca_list,
    469                 &sc->ca_list_size, &data,
    470                 GNUTLS_X509_FMT_PEM, 0);
    471 
    472         if (rv < 0) {
    473             return apr_psprintf(parms->pool,
    474                     "GnuTLS: Failed to load "
    475                     "Client CA File '%s': (%d) %s",
    476                     file, rv, gnutls_strerror(rv));
    477         }
    478     }
    479 
    480     apr_pool_destroy(spool);
     805    mgs_srvconf_rec *sc =
     806        (mgs_srvconf_rec *) ap_get_module_config(parms->server->
     807                                                 module_config,
     808                                                 &gnutls_module);
     809
     810    sc->x509_ca_file = ap_server_root_relative(parms->pool, arg);
     811
    481812    return NULL;
    482813}
     
    484815const char *mgs_set_keyring_file(cmd_parms * parms, void *dummy __attribute__((unused)),
    485816        const char *arg) {
    486     int rv;
    487     const char *file;
    488     apr_pool_t *spool;
    489     gnutls_datum_t data;
    490 
    491     mgs_srvconf_rec *sc =
    492             (mgs_srvconf_rec *) ap_get_module_config(parms->server->
    493             module_config,
    494             &gnutls_module);
    495     apr_pool_create(&spool, parms->pool);
    496 
    497     file = ap_server_root_relative(spool, arg);
    498 
    499     if (load_datum_from_file(spool, file, &data) != 0) {
    500         return apr_psprintf(parms->pool, "GnuTLS: Error Reading "
    501                 "Keyring File '%s'", file);
    502     }
    503 
    504     rv = gnutls_openpgp_keyring_init(&sc->pgp_list);
    505     if (rv < 0) {
    506         return apr_psprintf(parms->pool,
    507                 "GnuTLS: Failed to initialize"
    508                 "keyring: (%d) %s", rv,
    509                 gnutls_strerror(rv));
    510     }
    511 
    512     rv = gnutls_openpgp_keyring_import(sc->pgp_list, &data,
    513             GNUTLS_OPENPGP_FMT_BASE64);
    514     if (rv < 0) {
    515         return apr_psprintf(parms->pool, "GnuTLS: Failed to load "
    516                 "Keyring File '%s': (%d) %s", file, rv,
    517                 gnutls_strerror(rv));
    518     }
    519 
    520     apr_pool_destroy(spool);
     817    mgs_srvconf_rec *sc =
     818        (mgs_srvconf_rec *) ap_get_module_config(parms->server->
     819                                                 module_config,
     820                                                 &gnutls_module);
     821
     822    sc->pgp_ring_file = ap_server_root_relative(parms->pool, arg);
     823
    521824    return NULL;
    522825}
     
    525828        const char *arg) {
    526829
    527     mgs_srvconf_rec *sc =(mgs_srvconf_rec *)
    528             ap_get_module_config(parms->server->module_config, &gnutls_module);
     830    mgs_srvconf_rec *sc = (mgs_srvconf_rec *)
     831        ap_get_module_config(parms->server->module_config, &gnutls_module);
    529832
    530833    if (!strcasecmp(arg, "On")) {
    531         sc->proxy_enabled = GNUTLS_ENABLED_TRUE;
     834        sc->proxy_enabled = GNUTLS_ENABLED_TRUE;
    532835    } else if (!strcasecmp(arg, "Off")) {
    533         sc->proxy_enabled = GNUTLS_ENABLED_FALSE;
     836        sc->proxy_enabled = GNUTLS_ENABLED_FALSE;
    534837    } else {
    535         return "SSLProxyEngine must be set to 'On' or 'Off'";
     838        return "SSLProxyEngine must be set to 'On' or 'Off'";
    536839    }
    537840
     
    542845        const char *arg) {
    543846    mgs_srvconf_rec *sc =
    544             (mgs_srvconf_rec *) ap_get_module_config(parms->server->
    545             module_config,
    546             &gnutls_module);
     847        (mgs_srvconf_rec *) ap_get_module_config(parms->server->
     848                                                module_config,
     849                                                &gnutls_module);
    547850    if (!strcasecmp(arg, "On")) {
    548         sc->enabled = GNUTLS_ENABLED_TRUE;
     851        sc->enabled = GNUTLS_ENABLED_TRUE;
    549852    } else if (!strcasecmp(arg, "Off")) {
    550         sc->enabled = GNUTLS_ENABLED_FALSE;
     853        sc->enabled = GNUTLS_ENABLED_FALSE;
    551854    } else {
    552         return "GnuTLSEnable must be set to 'On' or 'Off'";
     855        return "GnuTLSEnable must be set to 'On' or 'Off'";
    553856    }
    554857
     
    559862    mgs_srvconf_rec *sc = (mgs_srvconf_rec *) ap_get_module_config(parms->server->module_config, &gnutls_module);
    560863    if (!strcasecmp(arg, "On")) {
    561         sc->export_certificates_size = 16 * 1024;
     864        sc->export_certificates_size = 16 * 1024;
    562865    } else if (!strcasecmp(arg, "Off")) {
    563         sc->export_certificates_size = 0;
     866        sc->export_certificates_size = 0;
    564867    } else {
    565         char* endptr;
    566         sc->export_certificates_size = strtol(arg, &endptr, 10);
    567         while (apr_isspace(*endptr)) endptr++;
    568         if (*endptr == '\0' || *endptr == 'b' || *endptr == 'B') {
    569             ;
    570         } else if (*endptr == 'k' || *endptr == 'K') {
    571             sc->export_certificates_size *= 1024;
    572         } else {
    573             return "GnuTLSExportCertificates must be set to a size (in bytes) or 'On' or 'Off'";
    574         }
     868        char *endptr;
     869        sc->export_certificates_size = strtol(arg, &endptr, 10);
     870        while (apr_isspace(*endptr))
     871            endptr++;
     872        if (*endptr == '\0' || *endptr == 'b' || *endptr == 'B') {
     873            ;
     874        } else if (*endptr == 'k' || *endptr == 'K') {
     875            sc->export_certificates_size *= 1024;
     876        } else {
     877            return
     878                "GnuTLSExportCertificates must be set to a size (in bytes) or 'On' or 'Off'";
     879        }
    575880    }
    576881
     
    598903    gnutls_priority_t *prio = NULL;
    599904    if (!strcasecmp(parms->directive->directive, "GnuTLSPriorities"))
    600         prio = &sc->priorities;
     905    {
     906        /* save string to be handled in mgs_load_files
     907         *
     908         * TODO: return to one wany of handling priorities for front
     909         * end and proxy connections */
     910        sc->priorities_str = apr_pstrdup(parms->pool, arg);
     911        return NULL;
     912        /* prio = &sc->priorities; */
     913    }
    601914    else if (!strcasecmp(parms->directive->directive, "GnuTLSProxyPriorities"))
    602915        prio = &sc->proxy_priorities;
     
    623936}
    624937
    625 static mgs_srvconf_rec *_mgs_config_server_create(apr_pool_t * p, char** err) {
    626     mgs_srvconf_rec *sc = apr_pcalloc(p, sizeof (*sc));
    627     int ret;
     938
     939
     940const char *mgs_set_pin(cmd_parms * parms, void *dummy __attribute__((unused)),
     941                        const char *arg)
     942{
     943
     944    mgs_srvconf_rec *sc = (mgs_srvconf_rec *)
     945        ap_get_module_config(parms->server->module_config, &gnutls_module);
     946
     947    sc->pin = apr_pstrdup(parms->pool, arg);
     948
     949    return NULL;
     950}
     951
     952const char *mgs_set_srk_pin(cmd_parms * parms,
     953                            void *dummy __attribute__((unused)),
     954                            const char *arg)
     955{
     956
     957    mgs_srvconf_rec *sc = (mgs_srvconf_rec *)
     958        ap_get_module_config(parms->server->module_config, &gnutls_module);
     959
     960    sc->srk_pin = apr_pstrdup(parms->pool, arg);
     961
     962    return NULL;
     963}
     964
     965
     966
     967static mgs_srvconf_rec *_mgs_config_server_create(apr_pool_t * p,
     968                                                  char **err __attribute__((unused)))
     969{
     970    mgs_srvconf_rec *sc = apr_pcalloc(p, sizeof(*sc));
    628971
    629972    sc->enabled = GNUTLS_ENABLED_UNSET;
    630973
    631     ret = gnutls_certificate_allocate_credentials(&sc->certs);
    632     if (ret < 0) {
    633         *err = apr_psprintf(p, "GnuTLS: Failed to initialize"
    634                             ": (%d) %s", ret,
    635                             gnutls_strerror(ret));
    636         return NULL;
    637     }
    638 
    639     ret = gnutls_anon_allocate_server_credentials(&sc->anon_creds);
    640     if (ret < 0) {
    641         *err = apr_psprintf(p, "GnuTLS: Failed to initialize"
    642                             ": (%d) %s", ret,
    643                             gnutls_strerror(ret));
    644         return NULL;
    645     }
    646 
    647     /* FIXME: not ideal, should be called only if SSLProxyEngine is
    648      * enabled */
    649     ret = gnutls_anon_allocate_client_credentials(&sc->anon_client_creds);
    650     if (ret < 0)
    651     {
    652         *err = apr_psprintf(p, "GnuTLS: Failed to initialize"
    653                             ": (%d) %s", ret,
    654                             gnutls_strerror(ret));
    655         return NULL;
    656     }
    657 
    658     sc->proxy_x509_key_file = NULL;
    659     sc->proxy_x509_cert_file = NULL;
    660     sc->proxy_x509_ca_file = NULL;
    661     sc->proxy_x509_crl_file = NULL;
    662     sc->proxy_priorities = NULL;
    663     ret = gnutls_certificate_allocate_credentials(&sc->proxy_x509_creds);
    664     if (ret < 0)
    665     {
    666         *err = apr_psprintf(p, "GnuTLS: Failed to initialize"
    667                             ": (%d) %s", ret,
    668                             gnutls_strerror(ret));
    669         return NULL;
    670     }
    671 
    672 #ifdef ENABLE_SRP
    673     ret = gnutls_srp_allocate_server_credentials(&sc->srp_creds);
    674     if (ret < 0) {
    675         *err =  apr_psprintf(p, "GnuTLS: Failed to initialize"
    676                              ": (%d) %s", ret,
    677                              gnutls_strerror(ret));
    678         return NULL;
    679     }
    680 
    681     sc->srp_tpasswd_conf_file = NULL;
    682     sc->srp_tpasswd_file = NULL;
    683 #endif
    684 
    685974    sc->privkey_x509 = NULL;
    686         /* Initialize all Certificate Chains */
    687     /* FIXME: how do we indicate that this is unset for a merge? (that
    688      * is, how can a subordinate server override the chain by setting
    689      * an empty one?  what would that even look like in the
    690      * configuration?) */
    691         sc->certs_x509_chain = malloc(MAX_CHAIN_SIZE * sizeof (*sc->certs_x509_chain));
     975    sc->privkey_pgp = NULL;
    692976    sc->certs_x509_chain_num = 0;
    693     sc->cache_timeout = -1; /* -1 means "unset" */
     977    sc->pin = NULL;
     978    sc->priorities_str = NULL;
     979    sc->cache_timeout = -1;     /* -1 means "unset" */
    694980    sc->cache_type = mgs_cache_unset;
    695981    sc->cache_config = NULL;
     
    701987    sc->client_verify_method = mgs_cvm_unset;
    702988
     989    sc->proxy_x509_key_file = NULL;
     990    sc->proxy_x509_cert_file = NULL;
     991    sc->proxy_x509_ca_file = NULL;
     992    sc->proxy_x509_crl_file = NULL;
     993    sc->proxy_priorities = NULL;
     994
    703995/* this relies on GnuTLS never changing the gnutls_certificate_request_t enum to define -1 */
    704996    sc->client_verify_mode = -1;
     
    7111003    char *err = NULL;
    7121004    mgs_srvconf_rec *sc = _mgs_config_server_create(p, &err);
    713     if (sc) return sc; else return err;
     1005    if (sc)
     1006        return sc;
     1007    else
     1008        return err;
    7141009}
    7151010
     
    7171012#define gnutls_srvconf_assign(t) sc->t = add->t
    7181013
    719 void *mgs_config_server_merge(apr_pool_t *p, void *BASE, void *ADD) {
     1014void *mgs_config_server_merge(apr_pool_t * p, void *BASE, void *ADD)
     1015{
    7201016    int i;
    7211017    char *err = NULL;
    722     mgs_srvconf_rec *base = (mgs_srvconf_rec *)BASE;
    723     mgs_srvconf_rec *add = (mgs_srvconf_rec *)ADD;
     1018    mgs_srvconf_rec *base = (mgs_srvconf_rec *) BASE;
     1019    mgs_srvconf_rec *add = (mgs_srvconf_rec *) ADD;
    7241020    mgs_srvconf_rec *sc = _mgs_config_server_create(p, &err);
    725     if (NULL == sc) return err;
     1021    if (NULL == sc)
     1022        return err;
    7261023
    7271024    gnutls_srvconf_merge(enabled, GNUTLS_ENABLED_UNSET);
     
    7331030    gnutls_srvconf_merge(srp_tpasswd_file, NULL);
    7341031    gnutls_srvconf_merge(srp_tpasswd_conf_file, NULL);
    735     gnutls_srvconf_merge(privkey_x509, NULL);
    736     gnutls_srvconf_merge(priorities, NULL);
    737     gnutls_srvconf_merge(dh_params, NULL);
     1032    gnutls_srvconf_merge(x509_cert_file, NULL);
     1033
     1034    gnutls_srvconf_merge(x509_key_file, NULL);
     1035    gnutls_srvconf_merge(x509_ca_file, NULL);
     1036    gnutls_srvconf_merge(pin, NULL);
     1037    gnutls_srvconf_merge(pgp_cert_file, NULL);
     1038    gnutls_srvconf_merge(pgp_key_file, NULL);
     1039    gnutls_srvconf_merge(pgp_ring_file, NULL);
     1040    gnutls_srvconf_merge(dh_file, NULL);
     1041    gnutls_srvconf_merge(priorities_str, NULL);
    7381042
    7391043    gnutls_srvconf_merge(proxy_x509_key_file, NULL);
     
    7461050     * properly disposed of before assigning in order to avoid leaks;
    7471051     * so at the moment, we can't actually have them in the config.
    748      * what happens during de-allocation?
    749 
    750      * This is probably leaky.
    751      */
     1052     * what happens during de-allocation? */
     1053    /* TODO: mgs_load_files takes care of most of these now, verify
     1054     * and clean up the following lines */
     1055    gnutls_srvconf_assign(ca_list);
     1056    gnutls_srvconf_assign(ca_list_size);
     1057    gnutls_srvconf_assign(cert_pgp);
     1058    gnutls_srvconf_assign(cert_crt_pgp);
     1059    gnutls_srvconf_assign(pgp_list);
    7521060    gnutls_srvconf_assign(certs);
    7531061    gnutls_srvconf_assign(anon_creds);
    754     gnutls_srvconf_assign(anon_client_creds);
    7551062    gnutls_srvconf_assign(srp_creds);
    7561063    gnutls_srvconf_assign(certs_x509_chain);
     1064    gnutls_srvconf_assign(certs_x509_crt_chain);
    7571065    gnutls_srvconf_assign(certs_x509_chain_num);
    7581066
     
    7611069    gnutls_srvconf_assign(cert_cn);
    7621070    for (i = 0; i < MAX_CERT_SAN; i++)
    763         gnutls_srvconf_assign(cert_san[i]);
    764     gnutls_srvconf_assign(ca_list);
    765     gnutls_srvconf_assign(ca_list_size);
    766     gnutls_srvconf_assign(cert_pgp);
    767     gnutls_srvconf_assign(pgp_list);
    768     gnutls_srvconf_assign(privkey_pgp);
     1071        gnutls_srvconf_assign(cert_san[i]);
    7691072
    7701073    return sc;
     
    7811084    mgs_dirconf_rec *add = (mgs_dirconf_rec *) addv;
    7821085
    783     new = (mgs_dirconf_rec *) apr_pcalloc(p, sizeof (mgs_dirconf_rec));
     1086    new = (mgs_dirconf_rec *) apr_pcalloc(p, sizeof(mgs_dirconf_rec));
    7841087    new->client_verify_mode = add->client_verify_mode;
    7851088    return new;
     
    7921095    return dc;
    7931096}
     1097
     1098
    7941099
    7951100/*
  • src/gnutls_hooks.c

    r73f6f12 r2cde026d  
    175175
    176176static int cert_retrieve_fn(gnutls_session_t session,
    177                                                         const gnutls_datum_t * req_ca_rdn __attribute__((unused)), int nreqs __attribute__((unused)),
    178                                                         const gnutls_pk_algorithm_t * pk_algos __attribute__((unused)), int pk_algos_length __attribute__((unused)),
    179                                                         gnutls_retr2_st *ret) {
    180 
    181 
    182         _gnutls_log(debug_log_fp, "%s: %d\n", __func__, __LINE__);
    183 
    184         mgs_handle_t *ctxt;
     177                            const gnutls_datum_t * req_ca_rdn __attribute__((unused)),
     178                            int nreqs __attribute__((unused)),
     179                            const gnutls_pk_algorithm_t * pk_algos __attribute__((unused)),
     180                            int pk_algos_length __attribute__((unused)),
     181                            gnutls_pcert_st **pcerts,
     182                            unsigned int *pcert_length,
     183                            gnutls_privkey_t *privkey)
     184{
     185    _gnutls_log(debug_log_fp, "%s: %d\n", __func__, __LINE__);
     186
     187    mgs_handle_t *ctxt;
    185188
    186189    if (session == NULL) {
    187190                // ERROR INVALID SESSION
    188                 ret->ncerts = 0;
    189                 ret->deinit_all = 1;
    190191        return -1;
    191         }
     192    }
     193
    192194    ctxt = gnutls_transport_get_ptr(session);
    193195
    194196    if (gnutls_certificate_type_get(session) == GNUTLS_CRT_X509) {
    195197                // X509 CERTIFICATE
    196                 ret->cert_type = GNUTLS_CRT_X509;
    197                 ret->key_type = GNUTLS_PRIVKEY_X509;
    198         ret->ncerts = ctxt->sc->certs_x509_chain_num;
    199         ret->deinit_all = 0;
    200         ret->cert.x509 = ctxt->sc->certs_x509_chain;
    201         ret->key.x509 = ctxt->sc->privkey_x509;
     198        *pcerts = ctxt->sc->certs_x509_chain;
     199        *pcert_length = ctxt->sc->certs_x509_chain_num;
     200        *privkey = ctxt->sc->privkey_x509;
    202201        return 0;
    203202    } else if (gnutls_certificate_type_get(session) == GNUTLS_CRT_OPENPGP) {
    204203                // OPENPGP CERTIFICATE
    205                 ret->cert_type = GNUTLS_CRT_OPENPGP;
    206                 ret->key_type = GNUTLS_PRIVKEY_OPENPGP;
    207         ret->ncerts = 1;
    208         ret->deinit_all = 0;
    209         ret->cert.pgp = ctxt->sc->cert_pgp;
    210         ret->key.pgp = ctxt->sc->privkey_pgp;
     204        *pcerts = ctxt->sc->cert_pgp;
     205        *pcert_length = 1;
     206        *privkey = ctxt->sc->privkey_pgp;
    211207        return 0;
    212208    } else {
    213209                // UNKNOWN CERTIFICATE
    214                 ret->ncerts = 0;
    215                 ret->deinit_all = 1;
    216210            return -1;
    217211        }
    218212}
    219 
    220 /* 2048-bit group parameters from SRP specification */
    221 const char static_dh_params[] = "-----BEGIN DH PARAMETERS-----\n"
    222         "MIIBBwKCAQCsa9tBMkqam/Fm3l4TiVgvr3K2ZRmH7gf8MZKUPbVgUKNzKcu0oJnt\n"
    223         "gZPgdXdnoT3VIxKrSwMxDc1/SKnaBP1Q6Ag5ae23Z7DPYJUXmhY6s2YaBfvV+qro\n"
    224         "KRipli8Lk7hV+XmT7Jde6qgNdArb9P90c1nQQdXDPqcdKB5EaxR3O8qXtDoj+4AW\n"
    225         "dr0gekNsZIHx0rkHhxdGGludMuaI+HdIVEUjtSSw1X1ep3onddLs+gMs+9v1L7N4\n"
    226         "YWAnkATleuavh05zA85TKZzMBBx7wwjYKlaY86jQw4JxrjX46dv7tpS1yAPYn3rk\n"
    227         "Nd4jbVJfVHWbZeNy/NaO8g+nER+eSv9zAgEC\n"
    228         "-----END DH PARAMETERS-----\n";
    229213
    230214/* Read the common name or the alternative name of the certificate.
     
    326310    }
    327311
    328 
    329312    s = base_server;
    330313    sc_base = (mgs_srvconf_rec *) ap_get_module_config(s->module_config, &gnutls_module);
    331314
    332     gnutls_dh_params_init(&dh_params);
    333 
    334     if (sc_base->dh_params == NULL) {
    335         gnutls_datum_t pdata = {
    336             (void *) static_dh_params,
    337             sizeof(static_dh_params)
    338         };
    339         rv = gnutls_dh_params_import_pkcs3(dh_params, &pdata, GNUTLS_X509_FMT_PEM);
    340         /* Generate DH Params
    341         int dh_bits = gnutls_sec_param_to_pk_bits(GNUTLS_PK_DH,
    342                 GNUTLS_SEC_PARAM_NORMAL);
    343         ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
    344             "GnuTLS: Generating DH Params of %i bits.  "
    345             "To avoid this use GnuTLSDHFile to specify DH Params for this host",
    346             dh_bits);
    347 #if MOD_GNUTLS_DEBUG
    348             ap_log_error(APLOG_MARK, APLOG_INFO, 0, s,
    349                     "GnuTLS: Generated DH Params of %i bits",dh_bits);
    350 #endif
    351         rv = gnutls_dh_params_generate2 (dh_params,dh_bits);
    352         */
    353         if (rv < 0) {
    354             ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
    355                     "GnuTLS: Unable to generate or load DH Params: (%d) %s",
    356                     rv, gnutls_strerror(rv));
    357             exit(rv);
    358         }
    359     } else {
    360         dh_params = sc_base->dh_params;
    361     }
    362315
    363316    rv = mgs_cache_post_config(p, s, sc_base);
     
    374327        sc->cache_config = sc_base->cache_config;
    375328        sc->cache_timeout = sc_base->cache_timeout;
     329
     330        rv = mgs_load_files(p, s);
     331        if (rv != 0) {
     332            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
     333                "GnuTLS: Loading required files failed."
     334                " Shutting Down.");
     335            exit(-1);
     336        }
    376337
    377338        /* defaults for unset values: */
     
    387348            sc->client_verify_method = mgs_cvm_cartel;
    388349
    389 
    390350        /* Check if the priorities have been set */
    391351        if (sc->priorities == NULL && sc->enabled == GNUTLS_ENABLED_TRUE) {
     
    405365        }
    406366
    407         gnutls_certificate_set_retrieve_function(sc->certs, cert_retrieve_fn);
    408 
    409 #ifdef ENABLE_SRP
    410         if (sc->srp_tpasswd_conf_file != NULL
    411                 && sc->srp_tpasswd_file != NULL) {
    412             rv = gnutls_srp_set_server_credentials_file
    413                     (sc->srp_creds, sc->srp_tpasswd_file,
    414                     sc->srp_tpasswd_conf_file);
    415 
    416             if (rv < 0 && sc->enabled == GNUTLS_ENABLED_TRUE) {
    417                 ap_log_error(APLOG_MARK, APLOG_STARTUP, 0,
    418                         s,
    419                         "[GnuTLS] - Host '%s:%d' is missing a "
    420                         "SRP password or conf File!",
    421                         s->server_hostname, s->port);
    422                 exit(-1);
    423             }
    424         }
     367        /* The call after this comment is a workaround for bug in
     368         * gnutls_certificate_set_retrieve_function2 that ignores
     369         * supported certificate types. Should be fixed in GnuTLS
     370         * 3.3.12.
     371         *
     372         * Details:
     373         * https://lists.gnupg.org/pipermail/gnutls-devel/2015-January/007377.html
     374         * Workaround from:
     375         * https://github.com/vanrein/tlspool/commit/4938102d3d1b086491d147e6c8e4e2a02825fc12 */
     376#if GNUTLS_VERSION_NUMBER < 0x030312
     377        gnutls_certificate_set_retrieve_function(sc->certs, (void *) exit);
    425378#endif
     379
     380        gnutls_certificate_set_retrieve_function2(sc->certs, cert_retrieve_fn);
    426381
    427382        if ((sc->certs_x509_chain == NULL || sc->certs_x509_chain_num < 1) &&
    428383            sc->cert_pgp == NULL && sc->enabled == GNUTLS_ENABLED_TRUE) {
    429384                        ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
    430                                                 "[GnuTLS] - Host '%s:%d' is missing a Certificate File!",
     385                                                "GnuTLS: Host '%s:%d' is missing a Certificate File!",
    431386                                                s->server_hostname, s->port);
    432387            exit(-1);
    433388        }
    434 
    435389        if (sc->enabled == GNUTLS_ENABLED_TRUE &&
    436             ((sc->certs_x509_chain != NULL && sc->certs_x509_chain_num > 0 && sc->privkey_x509 == NULL) ||
    437              (sc->cert_pgp != NULL && sc->privkey_pgp == NULL))) {
     390            ((sc->certs_x509_chain_num > 0 && sc->privkey_x509 == NULL) ||
     391             (sc->cert_crt_pgp[0] != NULL && sc->privkey_pgp == NULL))) {
    438392                        ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
    439                                                 "[GnuTLS] - Host '%s:%d' is missing a Private Key File!",
     393                                                "GnuTLS: Host '%s:%d' is missing a Private Key File!",
    440394                                                s->server_hostname, s->port);
    441395            exit(-1);
     
    445399            rv = -1;
    446400            if (sc->certs_x509_chain_num > 0) {
    447                 rv = read_crt_cn(s, p, sc->certs_x509_chain[0], &sc->cert_cn);
     401                rv = read_crt_cn(s, p, sc->certs_x509_crt_chain[0], &sc->cert_cn);
    448402            }
    449403            if (rv < 0 && sc->cert_pgp != NULL) {
    450                 rv = read_pgpcrt_cn(s, p, sc->cert_pgp, &sc->cert_cn);
     404                rv = read_pgpcrt_cn(s, p, sc->cert_crt_pgp[0], &sc->cert_cn);
    451405                        }
    452406
    453407            if (rv < 0) {
    454408                ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, s,
    455                                                         "[GnuTLS] - Cannot find a certificate for host '%s:%d'!",
     409                                                        "GnuTLS: Cannot find a certificate for host '%s:%d'!",
    456410                                                        s->server_hostname, s->port);
    457411                sc->cert_cn = NULL;
     
    494448}
    495449
    496 void mgs_hook_child_init(apr_pool_t * p, server_rec * s) {
     450void mgs_hook_child_init(apr_pool_t * p, server_rec *s) {
    497451    apr_status_t rv = APR_SUCCESS;
    498     mgs_srvconf_rec *sc = ap_get_module_config(s->module_config,
    499             &gnutls_module);
     452    mgs_srvconf_rec *sc =
     453        (mgs_srvconf_rec *) ap_get_module_config(s->module_config, &gnutls_module);
    500454
    501455    _gnutls_log(debug_log_fp, "%s: %d\n", __func__, __LINE__);
     456    /* if we use PKCS #11 reinitialize it */
     457
     458    if (mgs_pkcs11_reinit(s) < 0) {
     459            ap_log_error(APLOG_MARK, APLOG_EMERG, 0, s,
     460                    "GnuTLS: Failed to reinitialize PKCS #11");
     461            exit(-1);
     462    }
     463
    502464    if (sc->cache_type != mgs_cache_none) {
    503465        rv = mgs_cache_child_init(p, s, sc);
    504466        if (rv != APR_SUCCESS) {
    505467            ap_log_error(APLOG_MARK, APLOG_EMERG, rv, s,
    506                     "[GnuTLS] - Failed to run Cache Init");
     468                    "GnuTLS: Failed to run Cache Init");
    507469        }
    508470    }
     
    625587
    626588    if (tsc->certs_x509_chain_num > 0) {
    627         /* why are we doing this check? */
    628         ret = gnutls_x509_crt_check_hostname(tsc->certs_x509_chain[0], s->server_hostname);
     589        /* this check is there to warn administrator of any missing hostname
     590         * in the certificate. */
     591        ret = gnutls_x509_crt_check_hostname(tsc->certs_x509_crt_chain[0], s->server_hostname);
    629592        if (0 == ret)
    630             ap_log_error(APLOG_MARK, APLOG_INFO, 0, s,
    631                          "GnuTLS: Error checking certificate for hostname "
     593            ap_log_error(APLOG_MARK, APLOG_DEBUG, 0, s,
     594                         "GnuTLS: the certificate doesn't match requested hostname "
    632595                         "'%s'", s->server_hostname);
    633596    } else {
     
    956919
    957920    if (gnutls_certificate_type_get(ctxt->session) == GNUTLS_CRT_X509) {
    958                 mgs_add_common_cert_vars(r, ctxt->sc->certs_x509_chain[0], 0, ctxt->sc->export_certificates_size);
    959         } else if (gnutls_certificate_type_get(ctxt->session) == GNUTLS_CRT_OPENPGP) {
    960         mgs_add_common_pgpcert_vars(r, ctxt->sc->cert_pgp, 0, ctxt->sc->export_certificates_size);
    961         }
     921        mgs_add_common_cert_vars(r, ctxt->sc->certs_x509_crt_chain[0], 0, ctxt->sc->export_certificates_size);
     922    } else if (gnutls_certificate_type_get(ctxt->session) == GNUTLS_CRT_OPENPGP) {
     923        mgs_add_common_pgpcert_vars(r, ctxt->sc->cert_crt_pgp[0], 0, ctxt->sc->export_certificates_size);
     924    }
    962925
    963926    return rv;
     
    17751738    }
    17761739
     1740    /* allocate credentials structures */
     1741    err = gnutls_certificate_allocate_credentials(&sc->proxy_x509_creds);
     1742    if (err != GNUTLS_E_SUCCESS)
     1743    {
     1744        ap_log_error(APLOG_MARK, APLOG_ERR, 0, s,
     1745                     "%s: Failed to initialize proxy credentials: (%d) %s",
     1746                     __func__, err, gnutls_strerror(err));
     1747        return APR_EGENERAL;
     1748    }
     1749    err = gnutls_anon_allocate_client_credentials(&sc->anon_client_creds);
     1750    if (err != GNUTLS_E_SUCCESS)
     1751    {
     1752        ap_log_error(APLOG_MARK, APLOG_ERR, 0, s,
     1753                     "%s: Failed to initialize anon credentials for proxy: "
     1754                     "(%d) %s", __func__, err, gnutls_strerror(err));
     1755        return APR_EGENERAL;
     1756    }
     1757
    17771758    /* load certificate and key for client auth, if configured */
    17781759    if (sc->proxy_x509_key_file && sc->proxy_x509_cert_file)
  • src/mod_gnutls.c

    r73f6f12 r2cde026d  
    140140    RSRC_CONF | OR_AUTHCFG,
    141141    "Enable SSL Proxy Engine"),
     142    AP_INIT_RAW_ARGS("GnuTLSPIN", mgs_set_pin,
     143    NULL,
     144    RSRC_CONF,
     145    "The PIN to use in case of encrypted keys or PKCS #11 tokens."),
     146    AP_INIT_RAW_ARGS("GnuTLSSRKPIN", mgs_set_srk_pin,
     147    NULL,
     148    RSRC_CONF,
     149    "The SRK PIN to use in case of TPM keys."),
    142150    AP_INIT_TAKE1("GnuTLSClientVerify", mgs_set_client_verify,
    143151    NULL,
Note: See TracChangeset for help on using the changeset viewer.