diff options
author | Mathieu Trudel-Lapierre <mathieu.trudel-lapierre@canonical.com> | 2017-09-13 12:09:40 -0700 |
---|---|---|
committer | Mathieu Trudel-Lapierre <mathieu.trudel-lapierre@canonical.com> | 2017-09-13 12:09:40 -0700 |
commit | b6f94dbeacfc6f0a507413096189304c58dbe66c (patch) | |
tree | bce8c7db22209078618294c51d95a0c033aec7d9 /Cryptlib/OpenSSL/crypto/bio/bss_dgram.c | |
parent | 25f7fd1fb389a5f6356f353d16c5ead80dac6bbc (diff) | |
download | efi-boot-shim-upstream/13_git1505328970.9c1c35c5.tar.gz efi-boot-shim-upstream/13_git1505328970.9c1c35c5.zip |
New upstream version 13~git1505328970.9c1c35c5upstream/13_git1505328970.9c1c35c5
Diffstat (limited to 'Cryptlib/OpenSSL/crypto/bio/bss_dgram.c')
-rw-r--r-- | Cryptlib/OpenSSL/crypto/bio/bss_dgram.c | 417 |
1 files changed, 277 insertions, 140 deletions
diff --git a/Cryptlib/OpenSSL/crypto/bio/bss_dgram.c b/Cryptlib/OpenSSL/crypto/bio/bss_dgram.c index 6dfcc9ba..bdd7bf88 100644 --- a/Cryptlib/OpenSSL/crypto/bio/bss_dgram.c +++ b/Cryptlib/OpenSSL/crypto/bio/bss_dgram.c @@ -1,21 +1,70 @@ +/* crypto/bio/bio_dgram.c */ /* - * Copyright 2005-2016 The OpenSSL Project Authors. All Rights Reserved. + * DTLS implementation written by Nagendra Modadugu + * (nagendra@cs.stanford.edu) for the OpenSSL project 2005. + */ +/* ==================================================================== + * Copyright (c) 1999-2005 The OpenSSL Project. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * + * 3. All advertising materials mentioning features or use of this + * software must display the following acknowledgment: + * "This product includes software developed by the OpenSSL Project + * for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)" + * + * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to + * endorse or promote products derived from this software without + * prior written permission. For written permission, please contact + * openssl-core@OpenSSL.org. + * + * 5. Products derived from this software may not be called "OpenSSL" + * nor may "OpenSSL" appear in their names without prior written + * permission of the OpenSSL Project. + * + * 6. Redistributions of any form whatsoever must retain the following + * acknowledgment: + * "This product includes software developed by the OpenSSL Project + * for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)" + * + * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY + * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE OpenSSL PROJECT OR + * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * ==================================================================== + * + * This product includes cryptographic software written by Eric Young + * (eay@cryptsoft.com). This product includes software written by Tim + * Hudson (tjh@cryptsoft.com). * - * Licensed under the OpenSSL license (the "License"). You may not use - * this file except in compliance with the License. You can obtain a copy - * in the file LICENSE in the source distribution or at - * https://www.openssl.org/source/license.html */ #include <stdio.h> #include <errno.h> +#define USE_SOCKETS +#include "cryptlib.h" -#include "bio_lcl.h" +#include <openssl/bio.h> #ifndef OPENSSL_NO_DGRAM -# if !(defined(_WIN32) || defined(OPENSSL_SYS_VMS)) -# include <sys/time.h> -# endif # if defined(OPENSSL_SYS_VMS) # include <sys/timeb.h> # endif @@ -45,6 +94,12 @@ ((a)->s6_addr32[2] == htonl(0x0000ffff))) # endif +# ifdef WATT32 +# define sock_write SockWrite /* Watt-32 uses same names */ +# define sock_read SockRead +# define sock_puts SockPuts +# endif + static int dgram_write(BIO *h, const char *buf, int num); static int dgram_read(BIO *h, char *buf, int size); static int dgram_puts(BIO *h, const char *str); @@ -70,7 +125,7 @@ static int BIO_dgram_should_retry(int s); static void get_current_time(struct timeval *t); -static const BIO_METHOD methods_dgramp = { +static BIO_METHOD methods_dgramp = { BIO_TYPE_DGRAM, "datagram socket", dgram_write, @@ -84,7 +139,7 @@ static const BIO_METHOD methods_dgramp = { }; # ifndef OPENSSL_NO_SCTP -static const BIO_METHOD methods_dgramp_sctp = { +static BIO_METHOD methods_dgramp_sctp = { BIO_TYPE_DGRAM_SCTP, "datagram sctp socket", dgram_sctp_write, @@ -99,13 +154,18 @@ static const BIO_METHOD methods_dgramp_sctp = { # endif typedef struct bio_dgram_data_st { - BIO_ADDR peer; + union { + struct sockaddr sa; + struct sockaddr_in sa_in; +# if OPENSSL_USE_IPV6 + struct sockaddr_in6 sa_in6; +# endif + } peer; unsigned int connected; unsigned int _errno; unsigned int mtu; struct timeval next_timeout; struct timeval socket_timeout; - unsigned int peekmode; } bio_dgram_data; # ifndef OPENSSL_NO_SCTP @@ -116,7 +176,13 @@ typedef struct bio_dgram_sctp_save_message_st { } bio_dgram_sctp_save_message; typedef struct bio_dgram_sctp_data_st { - BIO_ADDR peer; + union { + struct sockaddr sa; + struct sockaddr_in sa_in; +# if OPENSSL_USE_IPV6 + struct sockaddr_in6 sa_in6; +# endif + } peer; unsigned int connected; unsigned int _errno; unsigned int mtu; @@ -134,7 +200,7 @@ typedef struct bio_dgram_sctp_data_st { } bio_dgram_sctp_data; # endif -const BIO_METHOD *BIO_s_datagram(void) +BIO_METHOD *BIO_s_datagram(void) { return (&methods_dgramp); } @@ -152,11 +218,17 @@ BIO *BIO_new_dgram(int fd, int close_flag) static int dgram_new(BIO *bi) { - bio_dgram_data *data = OPENSSL_zalloc(sizeof(*data)); + bio_dgram_data *data = NULL; + bi->init = 0; + bi->num = 0; + data = OPENSSL_malloc(sizeof(bio_dgram_data)); if (data == NULL) return 0; + memset(data, 0x00, sizeof(bio_dgram_data)); bi->ptr = data; + + bi->flags = 0; return (1); } @@ -170,7 +242,8 @@ static int dgram_free(BIO *a) return 0; data = (bio_dgram_data *)a->ptr; - OPENSSL_free(data); + if (data != NULL) + OPENSSL_free(data); return (1); } @@ -181,7 +254,7 @@ static int dgram_clear(BIO *a) return (0); if (a->shutdown) { if (a->init) { - BIO_closesocket(a->num); + SHUTDOWN2(a->num); } a->init = 0; a->flags = 0; @@ -244,7 +317,7 @@ static void dgram_adjust_rcv_timeout(BIO *b) } /* - * Adjust socket timeout if next handshake message timer will expire + * Adjust socket timeout if next handhake message timer will expire * earlier. */ if ((data->socket_timeout.tv_sec == 0 @@ -298,22 +371,39 @@ static int dgram_read(BIO *b, char *out, int outl) { int ret = 0; bio_dgram_data *data = (bio_dgram_data *)b->ptr; - int flags = 0; - BIO_ADDR peer; - socklen_t len = sizeof(peer); + struct { + /* + * See commentary in b_sock.c. <appro> + */ + union { + size_t s; + int i; + } len; + union { + struct sockaddr sa; + struct sockaddr_in sa_in; +# if OPENSSL_USE_IPV6 + struct sockaddr_in6 sa_in6; +# endif + } peer; + } sa; + + sa.len.s = 0; + sa.len.i = sizeof(sa.peer); if (out != NULL) { clear_socket_error(); - memset(&peer, 0, sizeof(peer)); + memset(&sa.peer, 0x00, sizeof(sa.peer)); dgram_adjust_rcv_timeout(b); - if (data->peekmode) - flags = MSG_PEEK; - ret = recvfrom(b->num, out, outl, flags, - BIO_ADDR_sockaddr_noconst(&peer), &len); + ret = recvfrom(b->num, out, outl, 0, &sa.peer.sa, (void *)&sa.len); + if (sizeof(sa.len.i) != sizeof(sa.len.s) && sa.len.i == 0) { + OPENSSL_assert(sa.len.s <= sizeof(sa.peer)); + sa.len.i = (int)sa.len.s; + } if (!data->connected && ret >= 0) - BIO_ctrl(b, BIO_CTRL_DGRAM_SET_PEER, 0, &peer); + BIO_ctrl(b, BIO_CTRL_DGRAM_SET_PEER, 0, &sa.peer); BIO_clear_retry_flags(b); if (ret < 0) { @@ -337,14 +427,18 @@ static int dgram_write(BIO *b, const char *in, int inl) if (data->connected) ret = writesocket(b->num, in, inl); else { - int peerlen = BIO_ADDR_sockaddr_size(&data->peer); + int peerlen = sizeof(data->peer); + if (data->peer.sa.sa_family == AF_INET) + peerlen = sizeof(data->peer.sa_in); +# if OPENSSL_USE_IPV6 + else if (data->peer.sa.sa_family == AF_INET6) + peerlen = sizeof(data->peer.sa_in6); +# endif # if defined(NETWARE_CLIB) && defined(NETWARE_BSDSOCK) - ret = sendto(b->num, (char *)in, inl, 0, - BIO_ADDR_sockaddr(&data->peer), peerlen); + ret = sendto(b->num, (char *)in, inl, 0, &data->peer.sa, peerlen); # else - ret = sendto(b->num, in, inl, 0, - BIO_ADDR_sockaddr(&data->peer), peerlen); + ret = sendto(b->num, in, inl, 0, &data->peer.sa, peerlen); # endif } @@ -353,6 +447,13 @@ static int dgram_write(BIO *b, const char *in, int inl) if (BIO_dgram_should_retry(ret)) { BIO_set_retry_write(b); data->_errno = get_last_socket_error(); + +# if 0 /* higher layers are responsible for querying + * MTU, if necessary */ + if (data->_errno == EMSGSIZE) + /* retrieve the new MTU */ + BIO_ctrl(b, BIO_CTRL_DGRAM_QUERY_MTU, 0, NULL); +# endif } } return (ret); @@ -362,31 +463,27 @@ static long dgram_get_mtu_overhead(bio_dgram_data *data) { long ret; - switch (BIO_ADDR_family(&data->peer)) { + switch (data->peer.sa.sa_family) { case AF_INET: /* * Assume this is UDP - 20 bytes for IP, 8 bytes for UDP */ ret = 28; break; -# ifdef AF_INET6 +# if OPENSSL_USE_IPV6 case AF_INET6: - { # ifdef IN6_IS_ADDR_V4MAPPED - struct in6_addr tmp_addr; - if (BIO_ADDR_rawaddress(&data->peer, &tmp_addr, NULL) - && IN6_IS_ADDR_V4MAPPED(&tmp_addr)) - /* - * Assume this is UDP - 20 bytes for IP, 8 bytes for UDP - */ - ret = 28; - else + if (IN6_IS_ADDR_V4MAPPED(&data->peer.sa_in6.sin6_addr)) + /* + * Assume this is UDP - 20 bytes for IP, 8 bytes for UDP + */ + ret = 28; + else # endif /* * Assume this is UDP - 40 bytes for IP, 8 bytes for UDP */ ret = 48; - } break; # endif default: @@ -401,14 +498,20 @@ static long dgram_ctrl(BIO *b, int cmd, long num, void *ptr) { long ret = 1; int *ip; + struct sockaddr *to = NULL; bio_dgram_data *data = NULL; int sockopt_val = 0; - int d_errno; # if defined(OPENSSL_SYS_LINUX) && (defined(IP_MTU_DISCOVER) || defined(IP_MTU)) socklen_t sockopt_len; /* assume that system supporting IP_MTU is * modern enough to define socklen_t */ socklen_t addr_len; - BIO_ADDR addr; + union { + struct sockaddr sa; + struct sockaddr_in s4; +# if OPENSSL_USE_IPV6 + struct sockaddr_in6 s6; +# endif + } addr; # endif data = (bio_dgram_data *)b->ptr; @@ -451,13 +554,35 @@ static long dgram_ctrl(BIO *b, int cmd, long num, void *ptr) ret = 1; break; case BIO_CTRL_DGRAM_CONNECT: - BIO_ADDR_make(&data->peer, BIO_ADDR_sockaddr((BIO_ADDR *)ptr)); + to = (struct sockaddr *)ptr; +# if 0 + if (connect(b->num, to, sizeof(struct sockaddr)) < 0) { + perror("connect"); + ret = 0; + } else { +# endif + switch (to->sa_family) { + case AF_INET: + memcpy(&data->peer, to, sizeof(data->peer.sa_in)); + break; +# if OPENSSL_USE_IPV6 + case AF_INET6: + memcpy(&data->peer, to, sizeof(data->peer.sa_in6)); + break; +# endif + default: + memcpy(&data->peer, to, sizeof(data->peer.sa)); + break; + } +# if 0 + } +# endif break; /* (Linux)kernel sets DF bit on outgoing IP packets */ case BIO_CTRL_DGRAM_MTU_DISCOVER: # if defined(OPENSSL_SYS_LINUX) && defined(IP_MTU_DISCOVER) && defined(IP_PMTUDISC_DO) addr_len = (socklen_t) sizeof(addr); - memset(&addr, 0, sizeof(addr)); + memset((void *)&addr, 0, sizeof(addr)); if (getsockname(b->num, &addr.sa, &addr_len) < 0) { ret = 0; break; @@ -481,14 +606,14 @@ static long dgram_ctrl(BIO *b, int cmd, long num, void *ptr) ret = -1; break; } -# else ret = -1; -# endif +# else break; +# endif case BIO_CTRL_DGRAM_QUERY_MTU: # if defined(OPENSSL_SYS_LINUX) && defined(IP_MTU) addr_len = (socklen_t) sizeof(addr); - memset(&addr, 0, sizeof(addr)); + memset((void *)&addr, 0, sizeof(addr)); if (getsockname(b->num, &addr.sa, &addr_len) < 0) { ret = 0; break; @@ -536,22 +661,18 @@ static long dgram_ctrl(BIO *b, int cmd, long num, void *ptr) break; case BIO_CTRL_DGRAM_GET_FALLBACK_MTU: ret = -dgram_get_mtu_overhead(data); - switch (BIO_ADDR_family(&data->peer)) { + switch (data->peer.sa.sa_family) { case AF_INET: ret += 576; break; # if OPENSSL_USE_IPV6 case AF_INET6: - { # ifdef IN6_IS_ADDR_V4MAPPED - struct in6_addr tmp_addr; - if (BIO_ADDR_rawaddress(&data->peer, &tmp_addr, NULL) - && IN6_IS_ADDR_V4MAPPED(&tmp_addr)) - ret += 576; - else + if (IN6_IS_ADDR_V4MAPPED(&data->peer.sa_in6.sin6_addr)) + ret += 576; + else # endif - ret += 1280; - } + ret += 1280; break; # endif default: @@ -561,29 +682,67 @@ static long dgram_ctrl(BIO *b, int cmd, long num, void *ptr) break; case BIO_CTRL_DGRAM_GET_MTU: return data->mtu; + break; case BIO_CTRL_DGRAM_SET_MTU: data->mtu = num; ret = num; break; case BIO_CTRL_DGRAM_SET_CONNECTED: - if (ptr != NULL) { + to = (struct sockaddr *)ptr; + + if (to != NULL) { data->connected = 1; - BIO_ADDR_make(&data->peer, BIO_ADDR_sockaddr((BIO_ADDR *)ptr)); + switch (to->sa_family) { + case AF_INET: + memcpy(&data->peer, to, sizeof(data->peer.sa_in)); + break; +# if OPENSSL_USE_IPV6 + case AF_INET6: + memcpy(&data->peer, to, sizeof(data->peer.sa_in6)); + break; +# endif + default: + memcpy(&data->peer, to, sizeof(data->peer.sa)); + break; + } } else { data->connected = 0; - memset(&data->peer, 0, sizeof(data->peer)); + memset(&(data->peer), 0x00, sizeof(data->peer)); } break; case BIO_CTRL_DGRAM_GET_PEER: - ret = BIO_ADDR_sockaddr_size(&data->peer); - /* FIXME: if num < ret, we will only return part of an address. - That should bee an error, no? */ + switch (data->peer.sa.sa_family) { + case AF_INET: + ret = sizeof(data->peer.sa_in); + break; +# if OPENSSL_USE_IPV6 + case AF_INET6: + ret = sizeof(data->peer.sa_in6); + break; +# endif + default: + ret = sizeof(data->peer.sa); + break; + } if (num == 0 || num > ret) num = ret; memcpy(ptr, &data->peer, (ret = num)); break; case BIO_CTRL_DGRAM_SET_PEER: - BIO_ADDR_make(&data->peer, BIO_ADDR_sockaddr((BIO_ADDR *)ptr)); + to = (struct sockaddr *)ptr; + switch (to->sa_family) { + case AF_INET: + memcpy(&data->peer, to, sizeof(data->peer.sa_in)); + break; +# if OPENSSL_USE_IPV6 + case AF_INET6: + memcpy(&data->peer, to, sizeof(data->peer.sa_in6)); + break; +# endif + default: + memcpy(&data->peer, to, sizeof(data->peer.sa)); + break; + } break; case BIO_CTRL_DGRAM_SET_NEXT_TIMEOUT: memcpy(&(data->next_timeout), ptr, sizeof(struct timeval)); @@ -706,11 +865,11 @@ static long dgram_ctrl(BIO *b, int cmd, long num, void *ptr) /* fall-through */ case BIO_CTRL_DGRAM_GET_RECV_TIMER_EXP: # ifdef OPENSSL_SYS_WINDOWS - d_errno = (data->_errno == WSAETIMEDOUT); + if (data->_errno == WSAETIMEDOUT) # else - d_errno = (data->_errno == EAGAIN); + if (data->_errno == EAGAIN) # endif - if (d_errno) { + { ret = 1; data->_errno = 0; } else @@ -783,9 +942,6 @@ static long dgram_ctrl(BIO *b, int cmd, long num, void *ptr) case BIO_CTRL_DGRAM_GET_MTU_OVERHEAD: ret = dgram_get_mtu_overhead(data); break; - case BIO_CTRL_DGRAM_SET_PEEK_MODE: - data->peekmode = (unsigned int)num; - break; default: ret = 0; break; @@ -803,7 +959,7 @@ static int dgram_puts(BIO *bp, const char *str) } # ifndef OPENSSL_NO_SCTP -const BIO_METHOD *BIO_s_datagram_sctp(void) +BIO_METHOD *BIO_s_datagram_sctp(void) { return (&methods_dgramp_sctp); } @@ -854,13 +1010,16 @@ BIO *BIO_new_dgram_sctp(int fd, int close_flag) * connected socket won't use it. */ sockopt_len = (socklen_t) (sizeof(sctp_assoc_t) + 256 * sizeof(uint8_t)); - authchunks = OPENSSL_zalloc(sockopt_len); - if (authchunks == NULL) { + authchunks = OPENSSL_malloc(sockopt_len); + if (!authchunks) { BIO_vfree(bio); return (NULL); } - ret = getsockopt(fd, IPPROTO_SCTP, SCTP_LOCAL_AUTH_CHUNKS, authchunks, + memset(authchunks, 0, sizeof(sockopt_len)); + ret = + getsockopt(fd, IPPROTO_SCTP, SCTP_LOCAL_AUTH_CHUNKS, authchunks, &sockopt_len); + if (ret < 0) { OPENSSL_free(authchunks); BIO_vfree(bio); @@ -883,7 +1042,7 @@ BIO *BIO_new_dgram_sctp(int fd, int close_flag) # ifdef SCTP_AUTHENTICATION_EVENT # ifdef SCTP_EVENT - memset(&event, 0, sizeof(event)); + memset(&event, 0, sizeof(struct sctp_event)); event.se_assoc_id = 0; event.se_type = SCTP_AUTHENTICATION_EVENT; event.se_on = 1; @@ -940,9 +1099,10 @@ static int dgram_sctp_new(BIO *bi) bi->init = 0; bi->num = 0; - data = OPENSSL_zalloc(sizeof(*data)); + data = OPENSSL_malloc(sizeof(bio_dgram_sctp_data)); if (data == NULL) return 0; + memset(data, 0x00, sizeof(bio_dgram_sctp_data)); # ifdef SCTP_PR_SCTP_NONE data->prinfo.pr_policy = SCTP_PR_SCTP_NONE; # endif @@ -963,7 +1123,8 @@ static int dgram_sctp_free(BIO *a) data = (bio_dgram_sctp_data *) a->ptr; if (data != NULL) { - OPENSSL_free(data->saved_message.data); + if (data->saved_message.data != NULL) + OPENSSL_free(data->saved_message.data); OPENSSL_free(data); } @@ -1003,7 +1164,8 @@ static int dgram_sctp_read(BIO *b, char *out, int outl) clear_socket_error(); do { - memset(&data->rcvinfo, 0, sizeof(data->rcvinfo)); + memset(&data->rcvinfo, 0x00, + sizeof(struct bio_dgram_sctp_rcvinfo)); iov.iov_base = out; iov.iov_len = outl; msg.msg_name = NULL; @@ -1072,13 +1234,9 @@ static int dgram_sctp_read(BIO *b, char *out, int outl) * it can be sent now. */ if (data->saved_message.length > 0) { - i = dgram_sctp_write(data->saved_message.bio, + dgram_sctp_write(data->saved_message.bio, data->saved_message.data, data->saved_message.length); - if (i < 0) { - ret = i; - break; - } OPENSSL_free(data->saved_message.data); data->saved_message.data = NULL; data->saved_message.length = 0; @@ -1086,7 +1244,7 @@ static int dgram_sctp_read(BIO *b, char *out, int outl) /* disable sender dry event */ # ifdef SCTP_EVENT - memset(&event, 0, sizeof(event)); + memset(&event, 0, sizeof(struct sctp_event)); event.se_assoc_id = 0; event.se_type = SCTP_SENDER_DRY_EVENT; event.se_on = 0; @@ -1192,11 +1350,11 @@ static int dgram_sctp_read(BIO *b, char *out, int outl) optlen = (socklen_t) (sizeof(sctp_assoc_t) + 256 * sizeof(uint8_t)); authchunks = OPENSSL_malloc(optlen); - if (authchunks == NULL) { + if (!authchunks) { BIOerr(BIO_F_DGRAM_SCTP_READ, ERR_R_MALLOC_FAILURE); return -1; } - memset(authchunks, 0, optlen); + memset(authchunks, 0, sizeof(optlen)); ii = getsockopt(b->num, IPPROTO_SCTP, SCTP_PEER_AUTH_CHUNKS, authchunks, &optlen); @@ -1223,14 +1381,6 @@ static int dgram_sctp_read(BIO *b, char *out, int outl) return (ret); } -/* - * dgram_sctp_write - send message on SCTP socket - * @b: BIO to write to - * @in: data to send - * @inl: amount of bytes in @in to send - * - * Returns -1 on error or the sent amount of bytes on success - */ static int dgram_sctp_write(BIO *b, const char *in, int inl) { int ret; @@ -1258,7 +1408,7 @@ static int dgram_sctp_write(BIO *b, const char *in, int inl) * parameters and flags. */ if (in[0] != 23) { - memset(&handshake_sinfo, 0, sizeof(handshake_sinfo)); + memset(&handshake_sinfo, 0x00, sizeof(struct bio_dgram_sctp_sndinfo)); # ifdef SCTP_SACK_IMMEDIATELY handshake_sinfo.snd_flags = SCTP_SACK_IMMEDIATELY; # endif @@ -1269,24 +1419,19 @@ static int dgram_sctp_write(BIO *b, const char *in, int inl) * If we have to send a shutdown alert message and the socket is not dry * yet, we have to save it and send it as soon as the socket gets dry. */ - if (data->save_shutdown) { - ret = BIO_dgram_sctp_wait_for_dry(b); - if (ret < 0) { + if (data->save_shutdown && !BIO_dgram_sctp_wait_for_dry(b)) { + char *tmp; + data->saved_message.bio = b; + if (!(tmp = OPENSSL_malloc(inl))) { + BIOerr(BIO_F_DGRAM_SCTP_WRITE, ERR_R_MALLOC_FAILURE); return -1; } - if (ret == 0) { - char *tmp; - data->saved_message.bio = b; - if ((tmp = OPENSSL_malloc(inl)) == NULL) { - BIOerr(BIO_F_DGRAM_SCTP_WRITE, ERR_R_MALLOC_FAILURE); - return -1; - } + if (data->saved_message.data) OPENSSL_free(data->saved_message.data); - data->saved_message.data = tmp; - memcpy(data->saved_message.data, in, inl); - data->saved_message.length = inl; - return inl; - } + data->saved_message.data = tmp; + memcpy(data->saved_message.data, in, inl); + data->saved_message.length = inl; + return inl; } iov[0].iov_base = (char *)in; @@ -1304,7 +1449,7 @@ static int dgram_sctp_write(BIO *b, const char *in, int inl) cmsg->cmsg_type = SCTP_SNDINFO; cmsg->cmsg_len = CMSG_LEN(sizeof(struct sctp_sndinfo)); sndinfo = (struct sctp_sndinfo *)CMSG_DATA(cmsg); - memset(sndinfo, 0, sizeof(*sndinfo)); + memset(sndinfo, 0, sizeof(struct sctp_sndinfo)); sndinfo->snd_sid = sinfo->snd_sid; sndinfo->snd_flags = sinfo->snd_flags; sndinfo->snd_ppid = sinfo->snd_ppid; @@ -1317,7 +1462,7 @@ static int dgram_sctp_write(BIO *b, const char *in, int inl) cmsg->cmsg_type = SCTP_PRINFO; cmsg->cmsg_len = CMSG_LEN(sizeof(struct sctp_prinfo)); prinfo = (struct sctp_prinfo *)CMSG_DATA(cmsg); - memset(prinfo, 0, sizeof(*prinfo)); + memset(prinfo, 0, sizeof(struct sctp_prinfo)); prinfo->pr_policy = pinfo->pr_policy; prinfo->pr_value = pinfo->pr_value; msg.msg_controllen += CMSG_SPACE(sizeof(struct sctp_prinfo)); @@ -1327,7 +1472,7 @@ static int dgram_sctp_write(BIO *b, const char *in, int inl) cmsg->cmsg_type = SCTP_SNDRCV; cmsg->cmsg_len = CMSG_LEN(sizeof(struct sctp_sndrcvinfo)); sndrcvinfo = (struct sctp_sndrcvinfo *)CMSG_DATA(cmsg); - memset(sndrcvinfo, 0, sizeof(*sndrcvinfo)); + memset(sndrcvinfo, 0, sizeof(struct sctp_sndrcvinfo)); sndrcvinfo->sinfo_stream = sinfo->snd_sid; sndrcvinfo->sinfo_flags = sinfo->snd_flags; # ifdef __FreeBSD__ @@ -1424,7 +1569,7 @@ static long dgram_sctp_ctrl(BIO *b, int cmd, long num, void *ptr) ret = -1; break; } - memset(authkey, 0, sockopt_len); + memset(authkey, 0x00, sockopt_len); authkey->sca_keynumber = authkeyid.scact_keynumber + 1; # ifndef __FreeBSD__ /* @@ -1604,24 +1749,10 @@ int BIO_dgram_sctp_notification_cb(BIO *b, return 0; } -/* - * BIO_dgram_sctp_wait_for_dry - Wait for SCTP SENDER_DRY event - * @b: The BIO to check for the dry event - * - * Wait until the peer confirms all packets have been received, and so that - * our kernel doesn't have anything to send anymore. This is only received by - * the peer's kernel, not the application. - * - * Returns: - * -1 on error - * 0 when not dry yet - * 1 when dry - */ int BIO_dgram_sctp_wait_for_dry(BIO *b) { int is_dry = 0; - int sockflags = 0; - int n, ret; + int n, sockflags, ret; union sctp_notification snp; struct msghdr msg; struct iovec iov; @@ -1635,7 +1766,7 @@ int BIO_dgram_sctp_wait_for_dry(BIO *b) /* set sender dry event */ # ifdef SCTP_EVENT - memset(&event, 0, sizeof(event)); + memset(&event, 0, sizeof(struct sctp_event)); event.se_assoc_id = 0; event.se_type = SCTP_SENDER_DRY_EVENT; event.se_on = 1; @@ -1658,7 +1789,7 @@ int BIO_dgram_sctp_wait_for_dry(BIO *b) return -1; /* peek for notification */ - memset(&snp, 0, sizeof(snp)); + memset(&snp, 0x00, sizeof(union sctp_notification)); iov.iov_base = (char *)&snp; iov.iov_len = sizeof(union sctp_notification); msg.msg_name = NULL; @@ -1680,7 +1811,7 @@ int BIO_dgram_sctp_wait_for_dry(BIO *b) /* if we find a notification, process it and try again if necessary */ while (msg.msg_flags & MSG_NOTIFICATION) { - memset(&snp, 0, sizeof(snp)); + memset(&snp, 0x00, sizeof(union sctp_notification)); iov.iov_base = (char *)&snp; iov.iov_len = sizeof(union sctp_notification); msg.msg_name = NULL; @@ -1705,7 +1836,7 @@ int BIO_dgram_sctp_wait_for_dry(BIO *b) /* disable sender dry event */ # ifdef SCTP_EVENT - memset(&event, 0, sizeof(event)); + memset(&event, 0, sizeof(struct sctp_event)); event.se_assoc_id = 0; event.se_type = SCTP_SENDER_DRY_EVENT; event.se_on = 0; @@ -1739,7 +1870,7 @@ int BIO_dgram_sctp_wait_for_dry(BIO *b) (void *)&snp); /* found notification, peek again */ - memset(&snp, 0, sizeof(snp)); + memset(&snp, 0x00, sizeof(union sctp_notification)); iov.iov_base = (char *)&snp; iov.iov_len = sizeof(union sctp_notification); msg.msg_name = NULL; @@ -1785,7 +1916,7 @@ int BIO_dgram_sctp_msg_waiting(BIO *b) /* Check if there are any messages waiting to be read */ do { - memset(&snp, 0, sizeof(snp)); + memset(&snp, 0x00, sizeof(union sctp_notification)); iov.iov_base = (char *)&snp; iov.iov_len = sizeof(union sctp_notification); msg.msg_name = NULL; @@ -1808,7 +1939,7 @@ int BIO_dgram_sctp_msg_waiting(BIO *b) dgram_sctp_handle_auth_free_key_event(b, &snp); # endif - memset(&snp, 0, sizeof(snp)); + memset(&snp, 0x00, sizeof(union sctp_notification)); iov.iov_base = (char *)&snp; iov.iov_len = sizeof(union sctp_notification); msg.msg_name = NULL; @@ -1871,6 +2002,12 @@ int BIO_dgram_non_fatal_error(int err) # if defined(WSAEWOULDBLOCK) case WSAEWOULDBLOCK: # endif + +# if 0 /* This appears to always be an error */ +# if defined(WSAENOTCONN) + case WSAENOTCONN: +# endif +# endif # endif # ifdef EWOULDBLOCK |