ee64fd9fe82208235dd9f696f5a2cf9cd6716c22
[openssl.git] / providers / implementations / storemgmt / file_store.c
1 /*
2  * Copyright 2020 The OpenSSL Project Authors. All Rights Reserved.
3  *
4  * Licensed under the Apache License 2.0 (the "License").  You may not use
5  * this file except in compliance with the License.  You can obtain a copy
6  * in the file LICENSE in the source distribution or at
7  * https://www.openssl.org/source/license.html
8  */
9
10 #include "e_os.h"                /* To get strncasecmp() on Windows */
11 #include <string.h>
12 #include <sys/stat.h>
13 #include <ctype.h>
14 #include <assert.h>
15
16 #include <openssl/core.h>
17 #include <openssl/core_dispatch.h>
18 #include <openssl/core_names.h>
19 #include <openssl/core_object.h>
20 #include <openssl/crypto.h>
21 #include <openssl/bio.h>
22 #include <openssl/err.h>
23 #include <openssl/buffer.h>
24 #include <openssl/params.h>
25 #include <openssl/decoder.h>
26 #include <openssl/store.h>       /* The OSSL_STORE_INFO type numbers */
27 #include "internal/o_dir.h"
28 #include "internal/pem.h"        /* For PVK and "blob" PEM headers */
29 #include "crypto/decoder.h"
30 #include "prov/implementations.h"
31 #include "prov/bio.h"
32 #include "prov/provider_ctx.h"
33 #include "prov/providercommonerr.h"
34 #include "file_store_local.h"
35
36 DEFINE_STACK_OF(OSSL_STORE_INFO)
37
38 #ifdef _WIN32
39 # define stat _stat
40 #endif
41
42 #ifndef S_ISDIR
43 # define S_ISDIR(a) (((a) & S_IFMT) == S_IFDIR)
44 #endif
45
46 static OSSL_FUNC_store_open_fn file_open;
47 static OSSL_FUNC_store_attach_fn file_attach;
48 static OSSL_FUNC_store_settable_ctx_params_fn file_settable_ctx_params;
49 static OSSL_FUNC_store_set_ctx_params_fn file_set_ctx_params;
50 static OSSL_FUNC_store_load_fn file_load;
51 static OSSL_FUNC_store_eof_fn file_eof;
52 static OSSL_FUNC_store_close_fn file_close;
53
54 /*
55  * This implementation makes full use of OSSL_DECODER, and then some.
56  * It uses its own internal decoder implementation that reads DER and
57  * passes that on to the data callback; this decoder is created with
58  * internal OpenSSL functions, thereby bypassing the need for a surrounding
59  * provider.  This is ok, since this is a local decoder, not meant for
60  * public consumption.  It also uses the libcrypto internal decoder
61  * setup function ossl_decoder_ctx_setup_for_EVP_PKEY(), to allow the
62  * last resort decoder to be added first (and thereby be executed last).
63  * Finally, it sets up its own construct and cleanup functions.
64  *
65  * Essentially, that makes this implementation a kind of glorified decoder.
66  */
67
68 struct file_ctx_st {
69     void *provctx;
70     char *uri;                   /* The URI we currently try to load */
71     enum {
72         IS_FILE = 0,             /* Read file and pass results */
73         IS_DIR                   /* Pass directory entry names */
74     } type;
75
76     /* Flag bits */
77     unsigned int flag_attached:1;
78     unsigned int flag_buffered:1;
79
80     union {
81         /* Used with |IS_FILE| */
82         struct {
83             BIO *file;
84
85             OSSL_DECODER_CTX *decoderctx;
86             char *input_type;
87             char *propq;    /* The properties we got as a parameter */
88         } file;
89
90         /* Used with |IS_DIR| */
91         struct {
92             OPENSSL_DIR_CTX *ctx;
93             int end_reached;
94
95             /*
96              * When a search expression is given, these are filled in.
97              * |search_name| contains the file basename to look for.
98              * The string is exactly 8 characters long.
99              */
100             char search_name[9];
101
102             /*
103              * The directory reading utility we have combines opening with
104              * reading the first name.  To make sure we can detect the end
105              * at the right time, we read early and cache the name.
106              */
107             const char *last_entry;
108             int last_errno;
109         } dir;
110     } _;
111
112     /* Expected object type.  May be unspecified */
113     int expected_type;
114 };
115
116 static void free_file_ctx(struct file_ctx_st *ctx)
117 {
118     if (ctx == NULL)
119         return;
120
121     OPENSSL_free(ctx->uri);
122     if (ctx->type != IS_DIR) {
123         OSSL_DECODER_CTX_free(ctx->_.file.decoderctx);
124         OPENSSL_free(ctx->_.file.propq);
125         OPENSSL_free(ctx->_.file.input_type);
126     }
127     OPENSSL_free(ctx);
128 }
129
130 static struct file_ctx_st *new_file_ctx(int type, const char *uri,
131                                         void *provctx)
132 {
133     struct file_ctx_st *ctx = NULL;
134
135     if ((ctx = OPENSSL_zalloc(sizeof(*ctx))) != NULL
136         && (uri == NULL || (ctx->uri = OPENSSL_strdup(uri)) != NULL)) {
137         ctx->type = type;
138         ctx->provctx = provctx;
139         return ctx;
140     }
141     free_file_ctx(ctx);
142     return NULL;
143 }
144
145 static OSSL_DECODER_CONSTRUCT file_load_construct;
146 static OSSL_DECODER_CLEANUP file_load_cleanup;
147
148 /*-
149  *  Opening / attaching streams and directories
150  *  -------------------------------------------
151  */
152
153 /*
154  * Function to service both file_open() and file_attach()
155  *
156  *
157  */
158 static struct file_ctx_st *file_open_stream(BIO *source, const char *uri,
159                                             const char *input_type,
160                                             void *provctx)
161 {
162     struct file_ctx_st *ctx;
163
164     if ((ctx = new_file_ctx(IS_FILE, uri, provctx)) == NULL
165         || (input_type != NULL
166             && (ctx->_.file.input_type =
167                 OPENSSL_strdup(input_type)) == NULL)) {
168         ERR_raise(ERR_LIB_PROV, ERR_R_MALLOC_FAILURE);
169         goto err;
170     }
171
172     ctx->_.file.file = source;
173
174     return ctx;
175  err:
176     free_file_ctx(ctx);
177     return NULL;
178 }
179
180 static void *file_open_dir(const char *path, const char *uri, void *provctx)
181 {
182     struct file_ctx_st *ctx;
183
184     if ((ctx = new_file_ctx(IS_DIR, uri, provctx)) == NULL) {
185         ERR_raise(ERR_LIB_PROV, ERR_R_MALLOC_FAILURE);
186         goto err;
187     }
188
189     ctx->_.dir.last_entry = OPENSSL_DIR_read(&ctx->_.dir.ctx, path);
190     ctx->_.dir.last_errno = errno;
191     if (ctx->_.dir.last_entry == NULL) {
192         if (ctx->_.dir.last_errno != 0) {
193             ERR_raise_data(ERR_LIB_SYS, ctx->_.dir.last_errno,
194                            "Calling OPENSSL_DIR_read(\"%s\")", path);
195             goto err;
196         }
197         ctx->_.dir.end_reached = 1;
198     }
199     return ctx;
200  err:
201     file_close(ctx);
202     return NULL;
203 }
204
205 static void *file_open(void *provctx, const char *uri)
206 {
207     struct file_ctx_st *ctx = NULL;
208     struct stat st;
209     struct {
210         const char *path;
211         unsigned int check_absolute:1;
212     } path_data[2];
213     size_t path_data_n = 0, i;
214     const char *path;
215     BIO *bio;
216
217     ERR_set_mark();
218
219     /*
220      * First step, just take the URI as is.
221      */
222     path_data[path_data_n].check_absolute = 0;
223     path_data[path_data_n++].path = uri;
224
225     /*
226      * Second step, if the URI appears to start with the 'file' scheme,
227      * extract the path and make that the second path to check.
228      * There's a special case if the URI also contains an authority, then
229      * the full URI shouldn't be used as a path anywhere.
230      */
231     if (strncasecmp(uri, "file:", 5) == 0) {
232         const char *p = &uri[5];
233
234         if (strncmp(&uri[5], "//", 2) == 0) {
235             path_data_n--;           /* Invalidate using the full URI */
236             if (strncasecmp(&uri[7], "localhost/", 10) == 0) {
237                 p = &uri[16];
238             } else if (uri[7] == '/') {
239                 p = &uri[7];
240             } else {
241                 ERR_clear_last_mark();
242                 ERR_raise(ERR_LIB_PROV, PROV_R_URI_AUTHORITY_UNSUPPORTED);
243                 return NULL;
244             }
245         }
246
247         path_data[path_data_n].check_absolute = 1;
248 #ifdef _WIN32
249         /* Windows file: URIs with a drive letter start with a / */
250         if (p[0] == '/' && p[2] == ':' && p[3] == '/') {
251             char c = tolower(p[1]);
252
253             if (c >= 'a' && c <= 'z') {
254                 p++;
255                 /* We know it's absolute, so no need to check */
256                 path_data[path_data_n].check_absolute = 0;
257             }
258         }
259 #endif
260         path_data[path_data_n++].path = p;
261     }
262
263
264     for (i = 0, path = NULL; path == NULL && i < path_data_n; i++) {
265         /*
266          * If the scheme "file" was an explicit part of the URI, the path must
267          * be absolute.  So says RFC 8089
268          */
269         if (path_data[i].check_absolute && path_data[i].path[0] != '/') {
270             ERR_clear_last_mark();
271             ERR_raise_data(ERR_LIB_PROV, PROV_R_PATH_MUST_BE_ABSOLUTE,
272                            "Given path=%s", path_data[i].path);
273             return NULL;
274         }
275
276         if (stat(path_data[i].path, &st) < 0) {
277             ERR_raise_data(ERR_LIB_SYS, errno,
278                            "calling stat(%s)",
279                            path_data[i].path);
280         } else {
281             path = path_data[i].path;
282         }
283     }
284     if (path == NULL) {
285         ERR_clear_last_mark();
286         return NULL;
287     }
288
289     /* Successfully found a working path, clear possible collected errors */
290     ERR_pop_to_mark();
291
292     if (S_ISDIR(st.st_mode))
293         ctx = file_open_dir(path, uri, provctx);
294     else if ((bio = BIO_new_file(path, "rb")) == NULL
295              || (ctx = file_open_stream(bio, uri, NULL, provctx)) == NULL)
296         BIO_free_all(bio);
297
298     return ctx;
299 }
300
301 /*
302  * Attached input streams must be treated very very carefully to avoid
303  * nasty surprises.
304  *
305  * This implementation tries to support input streams that can't be reset,
306  * such as standard input.  However, OSSL_DECODER assumes resettable streams,
307  * and because the PEM decoder may read quite a bit of the input file to skip
308  * past any non-PEM text that precedes the PEM block, we may need to detect
309  * if the input stream is a PEM file early.
310  *
311  * If the input stream supports BIO_tell(), we assume that it also supports
312  * BIO_seek(), making it a resettable stream and therefore safe to fully
313  * unleash OSSL_DECODER.
314  *
315  * If the input stream doesn't support BIO_tell(), we must assume that we
316  * have a non-resettable stream, and must tread carefully.  We do so by
317  * trying to detect if the input is PEM, MSBLOB or PVK, and if not, we
318  * assume that it's DER.
319  *
320  * To detect if an input stream is PEM, MSBLOB or PVK, we use the buffer BIO
321  * filter, which allows us a 4KiB resettable read-ahead.  We *hope* that 4KiB
322  * will be enough to find the start of the PEM block.
323  *
324  * It should be possible to use this same technique to detect other file
325  * types as well.
326  *
327  * An alternative technique would be to have an endlessly caching BIO filter.
328  * That would take away the need for all the detection here, and simply leave
329  * it for OSSL_DECODER to find out on its own while supporting its demand for
330  * resettable input streams.
331  * That's a possible future development.
332  */
333
334 # define INPUT_TYPE_ANY         NULL
335 # define INPUT_TYPE_DER         "DER"
336 # define INPUT_TYPE_PEM         "PEM"
337 # define INPUT_TYPE_MSBLOB      "MSBLOB"
338 # define INPUT_TYPE_PVK         "PVK"
339
340 void *file_attach(void *provctx, OSSL_CORE_BIO *cin)
341 {
342     BIO *new_bio = bio_new_from_core_bio(provctx, cin);
343     BIO *new_bio_tmp = NULL;
344     BIO *buff = NULL;
345     char peekbuf[4096] = { 0, };
346     int loc;
347     const char *input_type = NULL;
348     unsigned int flag_attached = 1;
349     unsigned int flag_buffered = 0;
350     struct file_ctx_st *ctx = NULL;
351
352     if (new_bio == NULL)
353         return 0;
354
355     /* Try to get the current position */
356     loc = BIO_tell(new_bio);
357
358     if ((buff = BIO_new(BIO_f_buffer())) == NULL
359         || (new_bio_tmp = BIO_push(buff, new_bio)) == NULL)
360         goto err;
361
362     /* Assumption, if we can't detect PEM */
363     input_type = INPUT_TYPE_DER;
364     flag_buffered = 1;
365     new_bio = new_bio_tmp;
366
367     if (BIO_buffer_peek(new_bio, peekbuf, sizeof(peekbuf) - 1) > 0) {
368 #ifndef OPENSSL_NO_DSA
369         const unsigned char *p = NULL;
370         unsigned int magic = 0, bitlen = 0;
371         int isdss = 0, ispub = -1;
372 # ifndef OPENSSL_NO_RC4
373         unsigned int saltlen = 0, keylen = 0;
374 # endif
375 #endif
376
377         peekbuf[sizeof(peekbuf) - 1] = '\0';
378         if (strstr(peekbuf, "-----BEGIN ") != NULL)
379             input_type = INPUT_TYPE_PEM;
380 #ifndef OPENSSL_NO_DSA
381         else if (p = (unsigned char *)peekbuf,
382                  ossl_do_blob_header(&p, sizeof(peekbuf), &magic, &bitlen,
383                                      &isdss, &ispub))
384             input_type = INPUT_TYPE_MSBLOB;
385 # ifndef OPENSSL_NO_RC4
386         else if (p = (unsigned char *)peekbuf,
387                  ossl_do_PVK_header(&p, sizeof(peekbuf), 0, &saltlen, &keylen))
388             input_type = INPUT_TYPE_PVK;
389 # endif
390 #endif
391     }
392
393     /*
394      * After peeking, we know that the underlying source BIO has moved ahead
395      * from its earlier position and that if it supports BIO_tell(), that
396      * should be a number that differs from |loc|.  Otherwise, we will get
397      * the same value, which may one of:
398      *
399      * -   zero (the source BIO doesn't support BIO_tell() / BIO_seek() /
400      *     BIO_reset())
401      * -   -1 (the underlying operating system / C library routines do not
402      *     support BIO_tell() / BIO_seek() / BIO_reset())
403      *
404      * If it turns out that the source BIO does support BIO_tell(), we pop
405      * the buffer BIO filter and mark this input as |INPUT_TYPE_ANY|, which
406      * fully unleashes OSSL_DECODER to do its thing.
407      */
408     if (BIO_tell(new_bio) != loc) {
409         /* In this case, anything goes */
410         input_type = INPUT_TYPE_ANY;
411
412         /* Restore the source BIO like it was when entering this function */
413         new_bio = BIO_pop(buff);
414         BIO_free(buff);
415         (void)BIO_seek(new_bio, loc);
416
417         flag_buffered = 0;
418     }
419
420     if ((ctx = file_open_stream(new_bio, NULL, input_type, provctx)) == NULL)
421         goto err;
422
423     ctx->flag_attached = flag_attached;
424     ctx->flag_buffered = flag_buffered;
425
426     return ctx;
427  err:
428     if (flag_buffered) {
429         new_bio = BIO_pop(buff);
430         BIO_free(buff);
431     }
432     BIO_free(new_bio);           /* Removes the provider BIO filter */
433     return NULL;
434 }
435
436 /*-
437  *  Setting parameters
438  *  ------------------
439  */
440
441 static const OSSL_PARAM *file_settable_ctx_params(void *provctx)
442 {
443     static const OSSL_PARAM known_settable_ctx_params[] = {
444         OSSL_PARAM_utf8_string(OSSL_STORE_PARAM_PROPERTIES, NULL, 0),
445         OSSL_PARAM_int(OSSL_STORE_PARAM_EXPECT, NULL),
446         OSSL_PARAM_octet_string(OSSL_STORE_PARAM_SUBJECT, NULL, 0),
447         OSSL_PARAM_END
448     };
449     return known_settable_ctx_params;
450 }
451
452 static int file_set_ctx_params(void *loaderctx, const OSSL_PARAM params[])
453 {
454     struct file_ctx_st *ctx = loaderctx;
455     const OSSL_PARAM *p;
456
457     p = OSSL_PARAM_locate_const(params, OSSL_STORE_PARAM_PROPERTIES);
458     if (p != NULL) {
459         OPENSSL_free(ctx->_.file.propq);
460         ctx->_.file.propq = NULL;
461         if (!OSSL_PARAM_get_utf8_string(p, &ctx->_.file.propq, 0))
462             return 0;
463     }
464     p = OSSL_PARAM_locate_const(params, OSSL_STORE_PARAM_EXPECT);
465     if (p != NULL && !OSSL_PARAM_get_int(p, &ctx->expected_type))
466         return 0;
467     p = OSSL_PARAM_locate_const(params, OSSL_STORE_PARAM_SUBJECT);
468     if (p != NULL) {
469         const unsigned char *der = NULL;
470         size_t der_len = 0;
471         X509_NAME *x509_name;
472         unsigned long hash;
473
474         if (ctx->type != IS_DIR) {
475             ERR_raise(ERR_LIB_PROV,
476                       PROV_R_SEARCH_ONLY_SUPPORTED_FOR_DIRECTORIES);
477             return 0;
478         }
479
480         if (!OSSL_PARAM_get_octet_string_ptr(p, (const void **)&der, &der_len)
481             || (x509_name = d2i_X509_NAME(NULL, &der, der_len)) == NULL)
482             return 0;
483         hash = X509_NAME_hash(x509_name);
484         BIO_snprintf(ctx->_.dir.search_name, sizeof(ctx->_.dir.search_name),
485                      "%08lx", hash);
486         X509_NAME_free(x509_name);
487     }
488     return 1;
489 }
490
491 /*-
492  *  Loading an object from a stream
493  *  -------------------------------
494  */
495
496 struct file_load_data_st {
497     OSSL_CALLBACK *object_cb;
498     void *object_cbarg;
499 };
500
501 static int file_load_construct(OSSL_DECODER_INSTANCE *decoder_inst,
502                                const OSSL_PARAM *params, void *construct_data)
503 {
504     struct file_load_data_st *data = construct_data;
505
506     /*
507      * At some point, we may find it justifiable to recognise PKCS#12 and
508      * handle it specially here, making |file_load()| return pass its
509      * contents one piece at ta time, like |e_loader_attic.c| does.
510      *
511      * However, that currently means parsing them out, which converts the
512      * DER encoded PKCS#12 into a bunch of EVP_PKEYs and X509s, just to
513      * have to re-encode them into DER to create an object abstraction for
514      * each of them.
515      * It's much simpler (less churn) to pass on the object abstraction we
516      * get to the load_result callback and leave it to that one to do the
517      * work.  If that's libcrypto code, we know that it has much better
518      * possibilities to handle the EVP_PKEYs and X509s without the extra
519      * churn.
520      */
521
522     return data->object_cb(params, data->object_cbarg);
523 }
524
525 void file_load_cleanup(void *construct_data)
526 {
527     /* Nothing to do */
528 }
529
530 static int file_setup_decoders(struct file_ctx_st *ctx)
531 {
532     EVP_PKEY *dummy; /* for OSSL_DECODER_CTX_new_by_EVP_PKEY() */
533     OPENSSL_CTX *libctx = PROV_CTX_get0_library_context(ctx->provctx);
534     OSSL_DECODER *to_obj = NULL; /* Last resort decoder */
535     OSSL_DECODER_INSTANCE *to_obj_inst = NULL;
536     OSSL_DECODER_CLEANUP *old_cleanup = NULL;
537     void *old_construct_data = NULL;
538     int ok = 0;
539
540     /* Setup for this session, so only if not already done */
541     if (ctx->_.file.decoderctx == NULL) {
542         if ((ctx->_.file.decoderctx = OSSL_DECODER_CTX_new()) == NULL) {
543             ERR_raise(ERR_LIB_PROV, ERR_R_MALLOC_FAILURE);
544             goto err;
545         }
546
547         /* Make sure the input type is set */
548         if (!OSSL_DECODER_CTX_set_input_type(ctx->_.file.decoderctx,
549                                              ctx->_.file.input_type)) {
550             ERR_raise(ERR_LIB_PROV, ERR_R_OSSL_DECODER_LIB);
551             goto err;
552         }
553
554         /*
555          * Create the internal last resort decoder implementation together
556          * with a "decoder instance".
557          * The decoder doesn't need any identification or to be attached to
558          * any provider, since it's only used locally.
559          */
560         to_obj = ossl_decoder_from_dispatch(0, &der_to_obj_algorithm, NULL);
561         if (to_obj == NULL)
562             goto err;
563         to_obj_inst = ossl_decoder_instance_new(to_obj, ctx->provctx);
564         if (to_obj_inst == NULL)
565             goto err;
566
567         if (!ossl_decoder_ctx_add_decoder_inst(ctx->_.file.decoderctx,
568                                                to_obj_inst)) {
569             ERR_raise(ERR_LIB_PROV, ERR_R_OSSL_DECODER_LIB);
570             goto err;
571         }
572
573         /*
574          * OSSL_DECODER_INSTANCE shouldn't be freed from this point on.
575          * That's going to happen whenever the OSSL_DECODER_CTX is freed.
576          */
577         to_obj_inst = NULL;
578
579         /*
580          * Add on the usual decoder context for keys, with a dummy object.
581          * Since we're setting up our own constructor, we don't need to care
582          * more than that...
583          */
584         if (!ossl_decoder_ctx_setup_for_EVP_PKEY(ctx->_.file.decoderctx, &dummy,
585                                                  libctx, ctx->_.file.propq)
586             || !OSSL_DECODER_CTX_add_extra(ctx->_.file.decoderctx,
587                                            libctx, ctx->_.file.propq)) {
588             ERR_raise(ERR_LIB_PROV, ERR_R_OSSL_DECODER_LIB);
589             goto err;
590         }
591
592         /*
593          * Then we throw away the installed finalizer data, and install our
594          * own instead.
595          */
596         old_cleanup = OSSL_DECODER_CTX_get_cleanup(ctx->_.file.decoderctx);
597         old_construct_data =
598             OSSL_DECODER_CTX_get_construct_data(ctx->_.file.decoderctx);
599         if (old_cleanup != NULL)
600             old_cleanup(old_construct_data);
601
602         /*
603          * Set the hooks.
604          */
605         if (!OSSL_DECODER_CTX_set_construct(ctx->_.file.decoderctx,
606                                             file_load_construct)
607             || !OSSL_DECODER_CTX_set_cleanup(ctx->_.file.decoderctx,
608                                              file_load_cleanup)) {
609             ERR_raise(ERR_LIB_PROV, ERR_R_OSSL_DECODER_LIB);
610             goto err;
611         }
612     }
613
614     ok = 1;
615  err:
616     OSSL_DECODER_free(to_obj);
617     return ok;
618 }
619
620 static int file_load_file(struct file_ctx_st *ctx,
621                           OSSL_CALLBACK *object_cb, void *object_cbarg,
622                           OSSL_PASSPHRASE_CALLBACK *pw_cb, void *pw_cbarg)
623 {
624     struct file_load_data_st data;
625
626     /* Setup the decoders (one time shot per session */
627
628     if (!file_setup_decoders(ctx))
629         return 0;
630
631     /* Setup for this object */
632
633     data.object_cb = object_cb;
634     data.object_cbarg = object_cbarg;
635     OSSL_DECODER_CTX_set_construct_data(ctx->_.file.decoderctx, &data);
636     OSSL_DECODER_CTX_set_passphrase_cb(ctx->_.file.decoderctx, pw_cb, pw_cbarg);
637
638     /* Launch */
639
640     return OSSL_DECODER_from_bio(ctx->_.file.decoderctx, ctx->_.file.file);
641 }
642
643 /*-
644  *  Loading a name object from a directory
645  *  --------------------------------------
646  */
647
648 static int ends_with_dirsep(const char *uri)
649 {
650     if (*uri != '\0')
651         uri += strlen(uri) - 1;
652 #if defined(__VMS)
653     if (*uri == ']' || *uri == '>' || *uri == ':')
654         return 1;
655 #elif defined(_WIN32)
656     if (*uri == '\\')
657         return 1;
658 #endif
659     return *uri == '/';
660 }
661
662 static char *file_name_to_uri(struct file_ctx_st *ctx, const char *name)
663 {
664     char *data = NULL;
665
666     assert(name != NULL);
667     {
668         const char *pathsep = ends_with_dirsep(ctx->uri) ? "" : "/";
669         long calculated_length = strlen(ctx->uri) + strlen(pathsep)
670             + strlen(name) + 1 /* \0 */;
671
672         data = OPENSSL_zalloc(calculated_length);
673         if (data == NULL) {
674             ERR_raise(ERR_LIB_PROV, ERR_R_MALLOC_FAILURE);
675             return NULL;
676         }
677
678         OPENSSL_strlcat(data, ctx->uri, calculated_length);
679         OPENSSL_strlcat(data, pathsep, calculated_length);
680         OPENSSL_strlcat(data, name, calculated_length);
681     }
682     return data;
683 }
684
685 static int file_name_check(struct file_ctx_st *ctx, const char *name)
686 {
687     const char *p = NULL;
688
689     /* If there are no search criteria, all names are accepted */
690     if (ctx->_.dir.search_name[0] == '\0')
691         return 1;
692
693     /* If the expected type isn't supported, no name is accepted */
694     if (ctx->expected_type != 0
695         && ctx->expected_type != OSSL_STORE_INFO_CERT
696         && ctx->expected_type != OSSL_STORE_INFO_CRL)
697         return 0;
698
699     /*
700      * First, check the basename
701      */
702     if (strncasecmp(name, ctx->_.dir.search_name,
703                     sizeof(ctx->_.dir.search_name) - 1) != 0
704         || name[sizeof(ctx->_.dir.search_name) - 1] != '.')
705         return 0;
706     p = &name[sizeof(ctx->_.dir.search_name)];
707
708     /*
709      * Then, if the expected type is a CRL, check that the extension starts
710      * with 'r'
711      */
712     if (*p == 'r') {
713         p++;
714         if (ctx->expected_type != 0
715             && ctx->expected_type != OSSL_STORE_INFO_CRL)
716             return 0;
717     } else if (ctx->expected_type == OSSL_STORE_INFO_CRL) {
718         return 0;
719     }
720
721     /*
722      * Last, check that the rest of the extension is a decimal number, at
723      * least one digit long.
724      */
725     if (!isdigit(*p))
726         return 0;
727     while (isdigit(*p))
728         p++;
729
730 #ifdef __VMS
731     /*
732      * One extra step here, check for a possible generation number.
733      */
734     if (*p == ';')
735         for (p++; *p != '\0'; p++)
736             if (!ossl_isdigit(*p))
737                 break;
738 #endif
739
740     /*
741      * If we've reached the end of the string at this point, we've successfully
742      * found a fitting file name.
743      */
744     return *p == '\0';
745 }
746
747 static int file_load_dir_entry(struct file_ctx_st *ctx,
748                                OSSL_CALLBACK *object_cb, void *object_cbarg,
749                                OSSL_PASSPHRASE_CALLBACK *pw_cb, void *pw_cbarg)
750 {
751     /* Prepare as much as possible in advance */
752     static const int object_type = OSSL_OBJECT_NAME;
753     OSSL_PARAM object[] = {
754         OSSL_PARAM_int(OSSL_OBJECT_PARAM_TYPE, (int *)&object_type),
755         OSSL_PARAM_utf8_string(OSSL_OBJECT_PARAM_DATA, NULL, 0),
756         OSSL_PARAM_END
757     };
758     char *newname = NULL;
759     int ok;
760
761     /* Loop until we get an error or until we have a suitable name */
762     do {
763         if (ctx->_.dir.last_entry == NULL) {
764             if (!ctx->_.dir.end_reached) {
765                 assert(ctx->_.dir.last_errno != 0);
766                 ERR_raise(ERR_LIB_SYS, ctx->_.dir.last_errno);
767             }
768             /* file_eof() will tell if EOF was reached */
769             return 0;
770         }
771
772         /* flag acceptable names */
773         if (ctx->_.dir.last_entry[0] != '.'
774             && file_name_check(ctx, ctx->_.dir.last_entry)) {
775
776             /* If we can't allocate the new name, we fail */
777             if ((newname =
778                  file_name_to_uri(ctx, ctx->_.dir.last_entry)) == NULL)
779                 return 0;
780         }
781
782         /*
783          * On the first call (with a NULL context), OPENSSL_DIR_read()
784          * cares about the second argument.  On the following calls, it
785          * only cares that it isn't NULL.  Therefore, we can safely give
786          * it our URI here.
787          */
788         ctx->_.dir.last_entry = OPENSSL_DIR_read(&ctx->_.dir.ctx, ctx->uri);
789         ctx->_.dir.last_errno = errno;
790         if (ctx->_.dir.last_entry == NULL && ctx->_.dir.last_errno == 0)
791             ctx->_.dir.end_reached = 1;
792     } while (newname == NULL);
793
794     object[1].data = newname;
795     object[1].data_size = strlen(newname);
796     ok = object_cb(object, object_cbarg);
797     OPENSSL_free(newname);
798     return ok;
799 }
800
801 /*-
802  *  Loading, local dispatcher
803  *  -------------------------
804  */
805
806 static int file_load(void *loaderctx,
807                      OSSL_CALLBACK *object_cb, void *object_cbarg,
808                      OSSL_PASSPHRASE_CALLBACK *pw_cb, void *pw_cbarg)
809 {
810     struct file_ctx_st *ctx = loaderctx;
811
812     switch (ctx->type) {
813     case IS_FILE:
814         return file_load_file(ctx, object_cb, object_cbarg, pw_cb, pw_cbarg);
815     case IS_DIR:
816         return
817             file_load_dir_entry(ctx, object_cb, object_cbarg, pw_cb, pw_cbarg);
818     default:
819         break;
820     }
821
822     /* ctx->type has an unexpected value */
823     assert(0);
824     return 0;
825 }
826
827 /*-
828  *  Eof detection and closing
829  *  -------------------------
830  */
831
832 static int file_eof(void *loaderctx)
833 {
834     struct file_ctx_st *ctx = loaderctx;
835
836     switch (ctx->type) {
837     case IS_DIR:
838         return ctx->_.dir.end_reached;
839     case IS_FILE:
840         /*
841          * BIO_pending() checks any filter BIO.
842          * BIO_eof() checks the source BIO.
843          */
844         return !BIO_pending(ctx->_.file.file)
845             && BIO_eof(ctx->_.file.file);
846     }
847
848     /* ctx->type has an unexpected value */
849     assert(0);
850     return 1;
851 }
852
853 static int file_close_dir(struct file_ctx_st *ctx)
854 {
855     if (ctx->_.dir.ctx != NULL)
856         OPENSSL_DIR_end(&ctx->_.dir.ctx);
857     free_file_ctx(ctx);
858     return 1;
859 }
860
861 static int file_close_stream(struct file_ctx_st *ctx)
862 {
863     if (ctx->flag_buffered) {
864         /*
865          * file_attach() pushed a BIO_f_buffer() on top of the regular BIO.
866          * Drop it.
867          */
868         BIO *buff = ctx->_.file.file;
869
870         /* Detach buff */
871         ctx->_.file.file = BIO_pop(ctx->_.file.file);
872
873         BIO_free(buff);
874     }
875
876     /*
877      * If it was attached, we only free the top, as that's the provider BIO
878      * filter.  Otherwise, it was entirely allocated by this implementation,
879      * and can safely be completely freed.
880      */
881     if (ctx->flag_attached)
882         BIO_free(ctx->_.file.file);
883     else
884         BIO_free_all(ctx->_.file.file);
885
886     /* To avoid double free */
887     ctx->_.file.file = NULL;
888
889     free_file_ctx(ctx);
890     return 1;
891 }
892
893 static int file_close(void *loaderctx)
894 {
895     struct file_ctx_st *ctx = loaderctx;
896
897     switch (ctx->type) {
898     case IS_DIR:
899         return file_close_dir(ctx);
900     case IS_FILE:
901         return file_close_stream(ctx);
902     }
903
904     /* ctx->type has an unexpected value */
905     assert(0);
906     return 1;
907 }
908
909 const OSSL_DISPATCH file_store_functions[] = {
910     { OSSL_FUNC_STORE_OPEN, (void (*)(void))file_open },
911     { OSSL_FUNC_STORE_ATTACH, (void (*)(void))file_attach },
912     { OSSL_FUNC_STORE_SETTABLE_CTX_PARAMS,
913       (void (*)(void))file_settable_ctx_params },
914     { OSSL_FUNC_STORE_SET_CTX_PARAMS, (void (*)(void))file_set_ctx_params },
915     { OSSL_FUNC_STORE_LOAD, (void (*)(void))file_load },
916     { OSSL_FUNC_STORE_EOF, (void (*)(void))file_eof },
917     { OSSL_FUNC_STORE_CLOSE, (void (*)(void))file_close },
918     { 0, NULL },
919 };