Вы не можете выбрать более 25 тем Темы должны начинаться с буквы или цифры, могут содержать дефисы(-) и должны содержать не более 35 символов.
 
 
 
 
 
 

804 строки
20 KiB

  1. /* ====================================================================
  2. * Copyright (c) 1998-2003 The OpenSSL Project. All rights reserved.
  3. *
  4. * Redistribution and use in source and binary forms, with or without
  5. * modification, are permitted provided that the following conditions
  6. * are met:
  7. *
  8. * 1. Redistributions of source code must retain the above copyright
  9. * notice, this list of conditions and the following disclaimer.
  10. *
  11. * 2. Redistributions in binary form must reproduce the above copyright
  12. * notice, this list of conditions and the following disclaimer in
  13. * the documentation and/or other materials provided with the
  14. * distribution.
  15. *
  16. * 3. All advertising materials mentioning features or use of this
  17. * software must display the following acknowledgment:
  18. * "This product includes software developed by the OpenSSL Project
  19. * for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
  20. *
  21. * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
  22. * endorse or promote products derived from this software without
  23. * prior written permission. For written permission, please contact
  24. * openssl-core@openssl.org.
  25. *
  26. * 5. Products derived from this software may not be called "OpenSSL"
  27. * nor may "OpenSSL" appear in their names without prior written
  28. * permission of the OpenSSL Project.
  29. *
  30. * 6. Redistributions of any form whatsoever must retain the following
  31. * acknowledgment:
  32. * "This product includes software developed by the OpenSSL Project
  33. * for use in the OpenSSL Toolkit (http://www.openssl.org/)"
  34. *
  35. * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
  36. * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  37. * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
  38. * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE OpenSSL PROJECT OR
  39. * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
  40. * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
  41. * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
  42. * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
  43. * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
  44. * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
  45. * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
  46. * OF THE POSSIBILITY OF SUCH DAMAGE.
  47. * ====================================================================
  48. *
  49. * This product includes cryptographic software written by Eric Young
  50. * (eay@cryptsoft.com). This product includes software written by Tim
  51. * Hudson (tjh@cryptsoft.com). */
  52. #include <openssl/bio.h>
  53. #include <assert.h>
  54. #include <string.h>
  55. #include <openssl/buf.h>
  56. #include <openssl/err.h>
  57. #include <openssl/mem.h>
  58. struct bio_bio_st {
  59. BIO *peer; /* NULL if buf == NULL.
  60. * If peer != NULL, then peer->ptr is also a bio_bio_st,
  61. * and its "peer" member points back to us.
  62. * peer != NULL iff init != 0 in the BIO. */
  63. /* This is for what we write (i.e. reading uses peer's struct): */
  64. int closed; /* valid iff peer != NULL */
  65. size_t len; /* valid iff buf != NULL; 0 if peer == NULL */
  66. size_t offset; /* valid iff buf != NULL; 0 if len == 0 */
  67. size_t size;
  68. uint8_t *buf; /* "size" elements (if != NULL) */
  69. char buf_externally_allocated; /* true iff buf was externally allocated. */
  70. char zero_copy_read_lock; /* true iff a zero copy read operation
  71. * is in progress. */
  72. char zero_copy_write_lock; /* true iff a zero copy write operation
  73. * is in progress. */
  74. size_t request; /* valid iff peer != NULL; 0 if len != 0,
  75. * otherwise set by peer to number of bytes
  76. * it (unsuccessfully) tried to read,
  77. * never more than buffer space (size-len) warrants. */
  78. };
  79. static int bio_new(BIO *bio) {
  80. struct bio_bio_st *b;
  81. b = OPENSSL_malloc(sizeof *b);
  82. if (b == NULL) {
  83. return 0;
  84. }
  85. memset(b, 0, sizeof(struct bio_bio_st));
  86. b->size = 17 * 1024; /* enough for one TLS record (just a default) */
  87. bio->ptr = b;
  88. return 1;
  89. }
  90. static void bio_destroy_pair(BIO *bio) {
  91. struct bio_bio_st *b = bio->ptr;
  92. BIO *peer_bio;
  93. struct bio_bio_st *peer_b;
  94. if (b == NULL) {
  95. return;
  96. }
  97. peer_bio = b->peer;
  98. if (peer_bio == NULL) {
  99. return;
  100. }
  101. peer_b = peer_bio->ptr;
  102. assert(peer_b != NULL);
  103. assert(peer_b->peer == bio);
  104. peer_b->peer = NULL;
  105. peer_bio->init = 0;
  106. assert(peer_b->buf != NULL);
  107. peer_b->len = 0;
  108. peer_b->offset = 0;
  109. b->peer = NULL;
  110. bio->init = 0;
  111. assert(b->buf != NULL);
  112. b->len = 0;
  113. b->offset = 0;
  114. }
  115. static int bio_free(BIO *bio) {
  116. struct bio_bio_st *b;
  117. if (bio == NULL) {
  118. return 0;
  119. }
  120. b = bio->ptr;
  121. assert(b != NULL);
  122. if (b->peer) {
  123. bio_destroy_pair(bio);
  124. }
  125. if (!b->buf_externally_allocated) {
  126. OPENSSL_free(b->buf);
  127. }
  128. OPENSSL_free(b);
  129. return 1;
  130. }
  131. static size_t bio_zero_copy_get_read_buf(struct bio_bio_st* peer_b,
  132. uint8_t** out_read_buf,
  133. size_t* out_buf_offset) {
  134. size_t max_available;
  135. if (peer_b->len > peer_b->size - peer_b->offset) {
  136. /* Only the first half of the ring buffer can be read. */
  137. max_available = peer_b->size - peer_b->offset;
  138. } else {
  139. max_available = peer_b->len;
  140. }
  141. *out_read_buf = peer_b->buf;
  142. *out_buf_offset = peer_b->offset;
  143. return max_available;
  144. }
  145. int BIO_zero_copy_get_read_buf(BIO* bio, uint8_t** out_read_buf,
  146. size_t* out_buf_offset,
  147. size_t* out_available_bytes) {
  148. struct bio_bio_st* b;
  149. struct bio_bio_st* peer_b;
  150. size_t max_available;
  151. *out_available_bytes = 0;
  152. BIO_clear_retry_flags(bio);
  153. if (!bio->init) {
  154. OPENSSL_PUT_ERROR(BIO, BIO_R_UNINITIALIZED);
  155. return 0;
  156. }
  157. b = bio->ptr;
  158. if (!b || !b->peer) {
  159. OPENSSL_PUT_ERROR(BIO, BIO_R_UNSUPPORTED_METHOD);
  160. return 0;
  161. }
  162. peer_b = b->peer->ptr;
  163. if (!peer_b || !peer_b->peer || peer_b->peer->ptr != b) {
  164. OPENSSL_PUT_ERROR(BIO, BIO_R_UNSUPPORTED_METHOD);
  165. return 0;
  166. }
  167. if (peer_b->zero_copy_read_lock) {
  168. OPENSSL_PUT_ERROR(BIO, BIO_R_INVALID_ARGUMENT);
  169. return 0;
  170. }
  171. peer_b->request = 0; /* Is not used by zero-copy API. */
  172. max_available =
  173. bio_zero_copy_get_read_buf(peer_b, out_read_buf, out_buf_offset);
  174. assert(peer_b->buf != NULL);
  175. if (max_available > 0) {
  176. peer_b->zero_copy_read_lock = 1;
  177. }
  178. *out_available_bytes = max_available;
  179. return 1;
  180. }
  181. int BIO_zero_copy_get_read_buf_done(BIO* bio, size_t bytes_read) {
  182. struct bio_bio_st* b;
  183. struct bio_bio_st* peer_b;
  184. size_t max_available;
  185. size_t dummy_read_offset;
  186. uint8_t* dummy_read_buf;
  187. assert(BIO_get_retry_flags(bio) == 0);
  188. if (!bio->init) {
  189. OPENSSL_PUT_ERROR(BIO, BIO_R_UNINITIALIZED);
  190. return 0;
  191. }
  192. b = bio->ptr;
  193. if (!b || !b->peer) {
  194. OPENSSL_PUT_ERROR(BIO, BIO_R_UNSUPPORTED_METHOD);
  195. return 0;
  196. }
  197. peer_b = b->peer->ptr;
  198. if (!peer_b || !peer_b->peer || peer_b->peer->ptr != b) {
  199. OPENSSL_PUT_ERROR(BIO, BIO_R_UNSUPPORTED_METHOD);
  200. return 0;
  201. }
  202. if (!peer_b->zero_copy_read_lock) {
  203. OPENSSL_PUT_ERROR(BIO, BIO_R_INVALID_ARGUMENT);
  204. return 0;
  205. }
  206. max_available =
  207. bio_zero_copy_get_read_buf(peer_b, &dummy_read_buf, &dummy_read_offset);
  208. if (bytes_read > max_available) {
  209. OPENSSL_PUT_ERROR(BIO, BIO_R_INVALID_ARGUMENT);
  210. return 0;
  211. }
  212. assert(peer_b->len >= bytes_read);
  213. peer_b->len -= bytes_read;
  214. assert(peer_b->offset + bytes_read <= peer_b->size);
  215. /* Move read offset. If zero_copy_write_lock == 1 we must advance the
  216. * offset even if buffer becomes empty, to make sure
  217. * write_offset = (offset + len) mod size does not change. */
  218. if (peer_b->offset + bytes_read == peer_b->size ||
  219. (!peer_b->zero_copy_write_lock && peer_b->len == 0)) {
  220. peer_b->offset = 0;
  221. } else {
  222. peer_b->offset += bytes_read;
  223. }
  224. bio->num_read += bytes_read;
  225. peer_b->zero_copy_read_lock = 0;
  226. return 1;
  227. }
  228. static size_t bio_zero_copy_get_write_buf(struct bio_bio_st* b,
  229. uint8_t** out_write_buf,
  230. size_t* out_buf_offset) {
  231. size_t write_offset;
  232. size_t max_available;
  233. assert(b->len <= b->size);
  234. write_offset = b->offset + b->len;
  235. if (write_offset >= b->size) {
  236. /* Only the first half of the ring buffer can be written to. */
  237. write_offset -= b->size;
  238. /* write up to the start of the ring buffer. */
  239. max_available = b->offset - write_offset;
  240. } else {
  241. /* write up to the end the buffer. */
  242. max_available = b->size - write_offset;
  243. }
  244. *out_write_buf = b->buf;
  245. *out_buf_offset = write_offset;
  246. return max_available;
  247. }
  248. int BIO_zero_copy_get_write_buf(BIO* bio, uint8_t** out_write_buf,
  249. size_t* out_buf_offset,
  250. size_t* out_available_bytes) {
  251. struct bio_bio_st* b;
  252. struct bio_bio_st* peer_b;
  253. size_t max_available;
  254. *out_available_bytes = 0;
  255. BIO_clear_retry_flags(bio);
  256. if (!bio->init) {
  257. OPENSSL_PUT_ERROR(BIO, BIO_R_UNINITIALIZED);
  258. return 0;
  259. }
  260. b = bio->ptr;
  261. if (!b || !b->buf || !b->peer) {
  262. OPENSSL_PUT_ERROR(BIO, BIO_R_UNSUPPORTED_METHOD);
  263. return 0;
  264. }
  265. peer_b = b->peer->ptr;
  266. if (!peer_b || !peer_b->peer || peer_b->peer->ptr != b) {
  267. OPENSSL_PUT_ERROR(BIO, BIO_R_UNSUPPORTED_METHOD);
  268. return 0;
  269. }
  270. assert(b->buf != NULL);
  271. if (b->zero_copy_write_lock) {
  272. OPENSSL_PUT_ERROR(BIO, BIO_R_INVALID_ARGUMENT);
  273. return 0;
  274. }
  275. b->request = 0;
  276. if (b->closed) {
  277. /* Bio is already closed. */
  278. OPENSSL_PUT_ERROR(BIO, BIO_R_BROKEN_PIPE);
  279. return 0;
  280. }
  281. max_available = bio_zero_copy_get_write_buf(b, out_write_buf, out_buf_offset);
  282. if (max_available > 0) {
  283. b->zero_copy_write_lock = 1;
  284. }
  285. *out_available_bytes = max_available;
  286. return 1;
  287. }
  288. int BIO_zero_copy_get_write_buf_done(BIO* bio, size_t bytes_written) {
  289. struct bio_bio_st* b;
  290. struct bio_bio_st* peer_b;
  291. size_t rest;
  292. size_t dummy_write_offset;
  293. uint8_t* dummy_write_buf;
  294. if (!bio->init) {
  295. OPENSSL_PUT_ERROR(BIO, BIO_R_UNINITIALIZED);
  296. return 0;
  297. }
  298. b = bio->ptr;
  299. if (!b || !b->buf || !b->peer) {
  300. OPENSSL_PUT_ERROR(BIO, BIO_R_UNSUPPORTED_METHOD);
  301. return 0;
  302. }
  303. peer_b = b->peer->ptr;
  304. if (!peer_b || !peer_b->peer || peer_b->peer->ptr != b) {
  305. OPENSSL_PUT_ERROR(BIO, BIO_R_UNSUPPORTED_METHOD);
  306. return 0;
  307. }
  308. b->request = 0;
  309. if (b->closed) {
  310. /* BIO is already closed. */
  311. OPENSSL_PUT_ERROR(BIO, BIO_R_BROKEN_PIPE);
  312. return 0;
  313. }
  314. if (!b->zero_copy_write_lock) {
  315. OPENSSL_PUT_ERROR(BIO, BIO_R_INVALID_ARGUMENT);
  316. return 0;
  317. }
  318. rest = bio_zero_copy_get_write_buf(b, &dummy_write_buf, &dummy_write_offset);
  319. if (bytes_written > rest) {
  320. OPENSSL_PUT_ERROR(BIO, BIO_R_INVALID_ARGUMENT);
  321. return 0;
  322. }
  323. bio->num_write += bytes_written;
  324. /* Move write offset. */
  325. b->len += bytes_written;
  326. b->zero_copy_write_lock = 0;
  327. return 1;
  328. }
  329. static int bio_read(BIO *bio, char *buf, int size_) {
  330. size_t size = size_;
  331. size_t rest;
  332. struct bio_bio_st *b, *peer_b;
  333. BIO_clear_retry_flags(bio);
  334. if (!bio->init) {
  335. return 0;
  336. }
  337. b = bio->ptr;
  338. assert(b != NULL);
  339. assert(b->peer != NULL);
  340. peer_b = b->peer->ptr;
  341. assert(peer_b != NULL);
  342. assert(peer_b->buf != NULL);
  343. peer_b->request = 0; /* will be set in "retry_read" situation */
  344. if (buf == NULL || size == 0 || peer_b->zero_copy_read_lock) {
  345. return 0;
  346. }
  347. if (peer_b->len == 0) {
  348. if (peer_b->closed) {
  349. return 0; /* writer has closed, and no data is left */
  350. } else {
  351. BIO_set_retry_read(bio); /* buffer is empty */
  352. if (size <= peer_b->size) {
  353. peer_b->request = size;
  354. } else {
  355. /* don't ask for more than the peer can
  356. * deliver in one write */
  357. peer_b->request = peer_b->size;
  358. }
  359. return -1;
  360. }
  361. }
  362. /* we can read */
  363. if (peer_b->len < size) {
  364. size = peer_b->len;
  365. }
  366. /* now read "size" bytes */
  367. rest = size;
  368. assert(rest > 0);
  369. /* one or two iterations */
  370. do {
  371. size_t chunk;
  372. assert(rest <= peer_b->len);
  373. if (peer_b->offset + rest <= peer_b->size) {
  374. chunk = rest;
  375. } else {
  376. /* wrap around ring buffer */
  377. chunk = peer_b->size - peer_b->offset;
  378. }
  379. assert(peer_b->offset + chunk <= peer_b->size);
  380. memcpy(buf, peer_b->buf + peer_b->offset, chunk);
  381. peer_b->len -= chunk;
  382. /* If zero_copy_write_lock == 1 we must advance the offset even if buffer
  383. * becomes empty, to make sure write_offset = (offset + len) % size
  384. * does not change. */
  385. if (peer_b->len || peer_b->zero_copy_write_lock) {
  386. peer_b->offset += chunk;
  387. assert(peer_b->offset <= peer_b->size);
  388. if (peer_b->offset == peer_b->size) {
  389. peer_b->offset = 0;
  390. }
  391. buf += chunk;
  392. } else {
  393. /* buffer now empty, no need to advance "buf" */
  394. assert(chunk == rest);
  395. peer_b->offset = 0;
  396. }
  397. rest -= chunk;
  398. } while (rest);
  399. return size;
  400. }
  401. static int bio_write(BIO *bio, const char *buf, int num_) {
  402. size_t num = num_;
  403. size_t rest;
  404. struct bio_bio_st *b;
  405. BIO_clear_retry_flags(bio);
  406. if (!bio->init || buf == NULL || num == 0) {
  407. return 0;
  408. }
  409. b = bio->ptr;
  410. assert(b != NULL);
  411. assert(b->peer != NULL);
  412. assert(b->buf != NULL);
  413. if (b->zero_copy_write_lock) {
  414. return 0;
  415. }
  416. b->request = 0;
  417. if (b->closed) {
  418. /* we already closed */
  419. OPENSSL_PUT_ERROR(BIO, BIO_R_BROKEN_PIPE);
  420. return -1;
  421. }
  422. assert(b->len <= b->size);
  423. if (b->len == b->size) {
  424. BIO_set_retry_write(bio); /* buffer is full */
  425. return -1;
  426. }
  427. /* we can write */
  428. if (num > b->size - b->len) {
  429. num = b->size - b->len;
  430. }
  431. /* now write "num" bytes */
  432. rest = num;
  433. assert(rest > 0);
  434. /* one or two iterations */
  435. do {
  436. size_t write_offset;
  437. size_t chunk;
  438. assert(b->len + rest <= b->size);
  439. write_offset = b->offset + b->len;
  440. if (write_offset >= b->size) {
  441. write_offset -= b->size;
  442. }
  443. /* b->buf[write_offset] is the first byte we can write to. */
  444. if (write_offset + rest <= b->size) {
  445. chunk = rest;
  446. } else {
  447. /* wrap around ring buffer */
  448. chunk = b->size - write_offset;
  449. }
  450. memcpy(b->buf + write_offset, buf, chunk);
  451. b->len += chunk;
  452. assert(b->len <= b->size);
  453. rest -= chunk;
  454. buf += chunk;
  455. } while (rest);
  456. return num;
  457. }
  458. static int bio_make_pair(BIO* bio1, BIO* bio2,
  459. size_t writebuf1_len, uint8_t* ext_writebuf1,
  460. size_t writebuf2_len, uint8_t* ext_writebuf2) {
  461. struct bio_bio_st *b1, *b2;
  462. assert(bio1 != NULL);
  463. assert(bio2 != NULL);
  464. b1 = bio1->ptr;
  465. b2 = bio2->ptr;
  466. if (b1->peer != NULL || b2->peer != NULL) {
  467. OPENSSL_PUT_ERROR(BIO, BIO_R_IN_USE);
  468. return 0;
  469. }
  470. assert(b1->buf_externally_allocated == 0);
  471. assert(b2->buf_externally_allocated == 0);
  472. if (b1->buf == NULL) {
  473. if (writebuf1_len) {
  474. b1->size = writebuf1_len;
  475. }
  476. if (!ext_writebuf1) {
  477. b1->buf_externally_allocated = 0;
  478. b1->buf = OPENSSL_malloc(b1->size);
  479. if (b1->buf == NULL) {
  480. OPENSSL_PUT_ERROR(BIO, ERR_R_MALLOC_FAILURE);
  481. return 0;
  482. }
  483. } else {
  484. b1->buf = ext_writebuf1;
  485. b1->buf_externally_allocated = 1;
  486. }
  487. b1->len = 0;
  488. b1->offset = 0;
  489. }
  490. if (b2->buf == NULL) {
  491. if (writebuf2_len) {
  492. b2->size = writebuf2_len;
  493. }
  494. if (!ext_writebuf2) {
  495. b2->buf_externally_allocated = 0;
  496. b2->buf = OPENSSL_malloc(b2->size);
  497. if (b2->buf == NULL) {
  498. OPENSSL_PUT_ERROR(BIO, ERR_R_MALLOC_FAILURE);
  499. return 0;
  500. }
  501. } else {
  502. b2->buf = ext_writebuf2;
  503. b2->buf_externally_allocated = 1;
  504. }
  505. b2->len = 0;
  506. b2->offset = 0;
  507. }
  508. b1->peer = bio2;
  509. b1->closed = 0;
  510. b1->request = 0;
  511. b1->zero_copy_read_lock = 0;
  512. b1->zero_copy_write_lock = 0;
  513. b2->peer = bio1;
  514. b2->closed = 0;
  515. b2->request = 0;
  516. b2->zero_copy_read_lock = 0;
  517. b2->zero_copy_write_lock = 0;
  518. bio1->init = 1;
  519. bio2->init = 1;
  520. return 1;
  521. }
  522. static long bio_ctrl(BIO *bio, int cmd, long num, void *ptr) {
  523. long ret;
  524. struct bio_bio_st *b = bio->ptr;
  525. assert(b != NULL);
  526. switch (cmd) {
  527. /* specific CTRL codes */
  528. case BIO_C_GET_WRITE_BUF_SIZE:
  529. ret = (long)b->size;
  530. break;
  531. case BIO_C_GET_WRITE_GUARANTEE:
  532. /* How many bytes can the caller feed to the next write
  533. * without having to keep any? */
  534. if (b->peer == NULL || b->closed) {
  535. ret = 0;
  536. } else {
  537. ret = (long)b->size - b->len;
  538. }
  539. break;
  540. case BIO_C_GET_READ_REQUEST:
  541. /* If the peer unsuccessfully tried to read, how many bytes
  542. * were requested? (As with BIO_CTRL_PENDING, that number
  543. * can usually be treated as boolean.) */
  544. ret = (long)b->request;
  545. break;
  546. case BIO_C_RESET_READ_REQUEST:
  547. /* Reset request. (Can be useful after read attempts
  548. * at the other side that are meant to be non-blocking,
  549. * e.g. when probing SSL_read to see if any data is
  550. * available.) */
  551. b->request = 0;
  552. ret = 1;
  553. break;
  554. case BIO_C_SHUTDOWN_WR:
  555. /* similar to shutdown(..., SHUT_WR) */
  556. b->closed = 1;
  557. ret = 1;
  558. break;
  559. /* standard CTRL codes follow */
  560. case BIO_CTRL_GET_CLOSE:
  561. ret = bio->shutdown;
  562. break;
  563. case BIO_CTRL_SET_CLOSE:
  564. bio->shutdown = (int)num;
  565. ret = 1;
  566. break;
  567. case BIO_CTRL_PENDING:
  568. if (b->peer != NULL) {
  569. struct bio_bio_st *peer_b = b->peer->ptr;
  570. ret = (long)peer_b->len;
  571. } else {
  572. ret = 0;
  573. }
  574. break;
  575. case BIO_CTRL_WPENDING:
  576. ret = 0;
  577. if (b->buf != NULL) {
  578. ret = (long)b->len;
  579. }
  580. break;
  581. case BIO_CTRL_FLUSH:
  582. ret = 1;
  583. break;
  584. case BIO_CTRL_EOF: {
  585. BIO *other_bio = ptr;
  586. if (other_bio) {
  587. struct bio_bio_st *other_b = other_bio->ptr;
  588. assert(other_b != NULL);
  589. ret = other_b->len == 0 && other_b->closed;
  590. } else {
  591. ret = 1;
  592. }
  593. } break;
  594. default:
  595. ret = 0;
  596. }
  597. return ret;
  598. }
  599. static int bio_puts(BIO *bio, const char *str) {
  600. return bio_write(bio, str, strlen(str));
  601. }
  602. static const BIO_METHOD methods_biop = {
  603. BIO_TYPE_BIO, "BIO pair", bio_write, bio_read,
  604. bio_puts, NULL /* no bio_gets */, bio_ctrl, bio_new,
  605. bio_free, NULL /* no bio_callback_ctrl */
  606. };
  607. static const BIO_METHOD *bio_s_bio(void) { return &methods_biop; }
  608. int BIO_new_bio_pair(BIO** bio1_p, size_t writebuf1,
  609. BIO** bio2_p, size_t writebuf2) {
  610. return BIO_new_bio_pair_external_buf(bio1_p, writebuf1, NULL, bio2_p,
  611. writebuf2, NULL);
  612. }
  613. int BIO_new_bio_pair_external_buf(BIO** bio1_p, size_t writebuf1_len,
  614. uint8_t* ext_writebuf1,
  615. BIO** bio2_p, size_t writebuf2_len,
  616. uint8_t* ext_writebuf2) {
  617. BIO *bio1 = NULL, *bio2 = NULL;
  618. int ret = 0;
  619. /* External buffers must have sizes greater than 0. */
  620. if ((ext_writebuf1 && !writebuf1_len) || (ext_writebuf2 && !writebuf2_len)) {
  621. goto err;
  622. }
  623. bio1 = BIO_new(bio_s_bio());
  624. if (bio1 == NULL) {
  625. goto err;
  626. }
  627. bio2 = BIO_new(bio_s_bio());
  628. if (bio2 == NULL) {
  629. goto err;
  630. }
  631. if (!bio_make_pair(bio1, bio2, writebuf1_len, ext_writebuf1, writebuf2_len,
  632. ext_writebuf2)) {
  633. goto err;
  634. }
  635. ret = 1;
  636. err:
  637. if (ret == 0) {
  638. BIO_free(bio1);
  639. bio1 = NULL;
  640. BIO_free(bio2);
  641. bio2 = NULL;
  642. }
  643. *bio1_p = bio1;
  644. *bio2_p = bio2;
  645. return ret;
  646. }
  647. size_t BIO_ctrl_get_read_request(BIO *bio) {
  648. return BIO_ctrl(bio, BIO_C_GET_READ_REQUEST, 0, NULL);
  649. }
  650. size_t BIO_ctrl_get_write_guarantee(BIO *bio) {
  651. return BIO_ctrl(bio, BIO_C_GET_WRITE_GUARANTEE, 0, NULL);
  652. }
  653. int BIO_shutdown_wr(BIO *bio) {
  654. return BIO_ctrl(bio, BIO_C_SHUTDOWN_WR, 0, NULL);
  655. }