2 * Copyright 2016-2024 The OpenSSL Project Authors. All Rights Reserved.
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
10 #include "bio_local.h"
11 #include "internal/thread_once.h"
13 CRYPTO_REF_COUNT bio_type_count
;
14 static CRYPTO_ONCE bio_type_init
= CRYPTO_ONCE_STATIC_INIT
;
16 DEFINE_RUN_ONCE_STATIC(do_bio_type_init
)
18 return CRYPTO_NEW_REF(&bio_type_count
, BIO_TYPE_START
);
21 int BIO_get_new_index(void)
25 if (!RUN_ONCE(&bio_type_init
, do_bio_type_init
)) {
26 /* Perhaps the error should be raised in do_bio_type_init()? */
27 ERR_raise(ERR_LIB_BIO
, ERR_R_CRYPTO_LIB
);
30 if (!CRYPTO_UP_REF(&bio_type_count
, &newval
))
32 if (newval
> BIO_TYPE_MASK
)
37 BIO_METHOD
*BIO_meth_new(int type
, const char *name
)
39 BIO_METHOD
*biom
= OPENSSL_zalloc(sizeof(BIO_METHOD
));
42 || (biom
->name
= OPENSSL_strdup(name
)) == NULL
) {
50 void BIO_meth_free(BIO_METHOD
*biom
)
53 OPENSSL_free(biom
->name
);
58 int (*BIO_meth_get_write(const BIO_METHOD
*biom
)) (BIO
*, const char *, int)
60 return biom
->bwrite_old
;
63 int (*BIO_meth_get_write_ex(const BIO_METHOD
*biom
)) (BIO
*, const char *, size_t,
69 /* Conversion for old style bwrite to new style */
70 int bwrite_conv(BIO
*bio
, const char *data
, size_t datal
, size_t *written
)
77 ret
= bio
->method
->bwrite_old(bio
, data
, (int)datal
);
84 *written
= (size_t)ret
;
89 int BIO_meth_set_write(BIO_METHOD
*biom
,
90 int (*bwrite
) (BIO
*, const char *, int))
92 biom
->bwrite_old
= bwrite
;
93 biom
->bwrite
= bwrite_conv
;
97 int BIO_meth_set_write_ex(BIO_METHOD
*biom
,
98 int (*bwrite
) (BIO
*, const char *, size_t, size_t *))
100 biom
->bwrite_old
= NULL
;
101 biom
->bwrite
= bwrite
;
105 int (*BIO_meth_get_read(const BIO_METHOD
*biom
)) (BIO
*, char *, int)
107 return biom
->bread_old
;
110 int (*BIO_meth_get_read_ex(const BIO_METHOD
*biom
)) (BIO
*, char *, size_t, size_t *)
115 /* Conversion for old style bread to new style */
116 int bread_conv(BIO
*bio
, char *data
, size_t datal
, size_t *readbytes
)
123 ret
= bio
->method
->bread_old(bio
, data
, (int)datal
);
130 *readbytes
= (size_t)ret
;
135 int BIO_meth_set_read(BIO_METHOD
*biom
,
136 int (*bread
) (BIO
*, char *, int))
138 biom
->bread_old
= bread
;
139 biom
->bread
= bread_conv
;
143 int BIO_meth_set_read_ex(BIO_METHOD
*biom
,
144 int (*bread
) (BIO
*, char *, size_t, size_t *))
146 biom
->bread_old
= NULL
;
151 int (*BIO_meth_get_puts(const BIO_METHOD
*biom
)) (BIO
*, const char *)
156 int BIO_meth_set_puts(BIO_METHOD
*biom
,
157 int (*bputs
) (BIO
*, const char *))
163 int (*BIO_meth_get_gets(const BIO_METHOD
*biom
)) (BIO
*, char *, int)
168 int BIO_meth_set_gets(BIO_METHOD
*biom
,
169 int (*bgets
) (BIO
*, char *, int))
175 long (*BIO_meth_get_ctrl(const BIO_METHOD
*biom
)) (BIO
*, int, long, void *)
180 int BIO_meth_set_ctrl(BIO_METHOD
*biom
,
181 long (*ctrl
) (BIO
*, int, long, void *))
187 int (*BIO_meth_get_create(const BIO_METHOD
*biom
)) (BIO
*)
192 int BIO_meth_set_create(BIO_METHOD
*biom
, int (*create
) (BIO
*))
194 biom
->create
= create
;
198 int (*BIO_meth_get_destroy(const BIO_METHOD
*biom
)) (BIO
*)
200 return biom
->destroy
;
203 int BIO_meth_set_destroy(BIO_METHOD
*biom
, int (*destroy
) (BIO
*))
205 biom
->destroy
= destroy
;
209 long (*BIO_meth_get_callback_ctrl(const BIO_METHOD
*biom
)) (BIO
*, int, BIO_info_cb
*)
211 return biom
->callback_ctrl
;
214 int BIO_meth_set_callback_ctrl(BIO_METHOD
*biom
,
215 long (*callback_ctrl
) (BIO
*, int,
218 biom
->callback_ctrl
= callback_ctrl
;
222 int BIO_meth_set_sendmmsg(BIO_METHOD
*biom
,
223 int (*bsendmmsg
) (BIO
*, BIO_MSG
*, size_t, size_t, uint64_t, size_t *))
225 biom
->bsendmmsg
= bsendmmsg
;
229 int (*BIO_meth_get_sendmmsg(const BIO_METHOD
*biom
))(BIO
*, BIO_MSG
*, size_t, size_t, uint64_t, size_t *) {
230 return biom
->bsendmmsg
;
233 int BIO_meth_set_recvmmsg(BIO_METHOD
*biom
,
234 int (*brecvmmsg
) (BIO
*, BIO_MSG
*, size_t, size_t, uint64_t, size_t *))
236 biom
->brecvmmsg
= brecvmmsg
;
240 int (*BIO_meth_get_recvmmsg(const BIO_METHOD
*biom
))(BIO
*, BIO_MSG
*, size_t, size_t, uint64_t, size_t *) {
241 return biom
->brecvmmsg
;