summaryrefslogtreecommitdiff
path: root/src/usr.bin/openssl/s_client.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/usr.bin/openssl/s_client.c')
-rw-r--r--src/usr.bin/openssl/s_client.c67
1 files changed, 41 insertions, 26 deletions
diff --git a/src/usr.bin/openssl/s_client.c b/src/usr.bin/openssl/s_client.c
index 988d799b97..94e24dacaa 100644
--- a/src/usr.bin/openssl/s_client.c
+++ b/src/usr.bin/openssl/s_client.c
@@ -1,4 +1,4 @@
1/* $OpenBSD: s_client.c,v 1.8 2014/11/18 20:54:28 krw Exp $ */ 1/* $OpenBSD: s_client.c,v 1.9 2014/12/02 19:44:49 deraadt Exp $ */
2/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) 2/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
3 * All rights reserved. 3 * All rights reserved.
4 * 4 *
@@ -137,7 +137,6 @@
137 137
138#include <sys/types.h> 138#include <sys/types.h>
139#include <sys/ioctl.h> 139#include <sys/ioctl.h>
140#include <sys/select.h>
141#include <sys/socket.h> 140#include <sys/socket.h>
142 141
143#include <netinet/in.h> 142#include <netinet/in.h>
@@ -150,6 +149,7 @@
150#include <stdlib.h> 149#include <stdlib.h>
151#include <string.h> 150#include <string.h>
152#include <unistd.h> 151#include <unistd.h>
152#include <poll.h>
153 153
154#include "apps.h" 154#include "apps.h"
155 155
@@ -334,11 +334,10 @@ s_client_main(int argc, char **argv)
334{ 334{
335 unsigned int off = 0, clr = 0; 335 unsigned int off = 0, clr = 0;
336 SSL *con = NULL; 336 SSL *con = NULL;
337 int s, k, width, state = 0, af = AF_UNSPEC; 337 int s, k, state = 0, af = AF_UNSPEC;
338 char *cbuf = NULL, *sbuf = NULL, *mbuf = NULL; 338 char *cbuf = NULL, *sbuf = NULL, *mbuf = NULL;
339 int cbuf_len, cbuf_off; 339 int cbuf_len, cbuf_off;
340 int sbuf_len, sbuf_off; 340 int sbuf_len, sbuf_off;
341 fd_set readfds, writefds;
342 char *port = PORT_STR; 341 char *port = PORT_STR;
343 int full_log = 1; 342 int full_log = 1;
344 char *host = SSL_HOST_NAME; 343 char *host = SSL_HOST_NAME;
@@ -361,7 +360,7 @@ s_client_main(int argc, char **argv)
361 int socket_type = SOCK_STREAM; 360 int socket_type = SOCK_STREAM;
362 BIO *sbio; 361 BIO *sbio;
363 int mbuf_len = 0; 362 int mbuf_len = 0;
364 struct timeval timeout, *timeoutp; 363 struct timeval timeout;
365 const char *errstr = NULL; 364 const char *errstr = NULL;
366#ifndef OPENSSL_NO_ENGINE 365#ifndef OPENSSL_NO_ENGINE
367 char *engine_id = NULL; 366 char *engine_id = NULL;
@@ -874,8 +873,6 @@ re_start:
874 SSL_set_connect_state(con); 873 SSL_set_connect_state(con);
875 874
876 /* ok, lets connect */ 875 /* ok, lets connect */
877 width = SSL_get_fd(con) + 1;
878
879 read_tty = 1; 876 read_tty = 1;
880 write_tty = 0; 877 write_tty = 0;
881 tty_on = 0; 878 tty_on = 0;
@@ -991,14 +988,12 @@ re_start:
991 mbuf[0] = 0; 988 mbuf[0] = 0;
992 } 989 }
993 for (;;) { 990 for (;;) {
994 FD_ZERO(&readfds); 991 struct pollfd pfd[3]; /* stdin, stdout, socket */
995 FD_ZERO(&writefds); 992 int ptimeout = -1;
996 993
997 if ((SSL_version(con) == DTLS1_VERSION) && 994 if ((SSL_version(con) == DTLS1_VERSION) &&
998 DTLSv1_get_timeout(con, &timeout)) 995 DTLSv1_get_timeout(con, &timeout))
999 timeoutp = &timeout; 996 ptimeout = timeout.tv_sec * 1000 + timeout.tv_usec / 1000;
1000 else
1001 timeoutp = NULL;
1002 997
1003 if (SSL_in_init(con) && !SSL_total_renegotiations(con)) { 998 if (SSL_in_init(con) && !SSL_total_renegotiations(con)) {
1004 in_init = 1; 999 in_init = 1;
@@ -1038,24 +1033,31 @@ re_start:
1038 1033
1039 ssl_pending = read_ssl && SSL_pending(con); 1034 ssl_pending = read_ssl && SSL_pending(con);
1040 1035
1041 /* XXX should add tests for fd_set overflow */ 1036 pfd[0].fd = -1;
1042 1037 pfd[1].fd = -1;
1043 if (!ssl_pending) { 1038 if (!ssl_pending) {
1044 if (tty_on) { 1039 if (tty_on) {
1045 if (read_tty) 1040 if (read_tty) {
1046 FD_SET(fileno(stdin), &readfds); 1041 pfd[0].fd = fileno(stdin);
1047 if (write_tty) 1042 pfd[0].events = POLLIN;
1048 FD_SET(fileno(stdout), &writefds); 1043 }
1044 if (write_tty) {
1045 pfd[1].fd = fileno(stdout);
1046 pfd[1].events = POLLOUT;
1047 }
1049 } 1048 }
1049
1050 pfd[2].fd = SSL_get_fd(con);
1051 pfd[2].events = 0;
1050 if (read_ssl) 1052 if (read_ssl)
1051 FD_SET(SSL_get_fd(con), &readfds); 1053 pfd[2].events |= POLLIN;
1052 if (write_ssl) 1054 if (write_ssl)
1053 FD_SET(SSL_get_fd(con), &writefds); 1055 pfd[2].events |= POLLOUT;
1056
1054/* printf("mode tty(%d %d%d) ssl(%d%d)\n", 1057/* printf("mode tty(%d %d%d) ssl(%d%d)\n",
1055 tty_on,read_tty,write_tty,read_ssl,write_ssl);*/ 1058 tty_on,read_tty,write_tty,read_ssl,write_ssl);*/
1056 1059
1057 i = select(width, &readfds, &writefds, 1060 i = poll(pfd, 3, ptimeout);
1058 NULL, timeoutp);
1059 if (i < 0) { 1061 if (i < 0) {
1060 BIO_printf(bio_err, "bad select %d\n", 1062 BIO_printf(bio_err, "bad select %d\n",
1061 errno); 1063 errno);
@@ -1066,7 +1068,11 @@ re_start:
1066 if ((SSL_version(con) == DTLS1_VERSION) && DTLSv1_handle_timeout(con) > 0) { 1068 if ((SSL_version(con) == DTLS1_VERSION) && DTLSv1_handle_timeout(con) > 0) {
1067 BIO_printf(bio_err, "TIMEOUT occured\n"); 1069 BIO_printf(bio_err, "TIMEOUT occured\n");
1068 } 1070 }
1069 if (!ssl_pending && FD_ISSET(SSL_get_fd(con), &writefds)) { 1071 if (!ssl_pending && (pfd[2].revents & (POLLOUT|POLLERR|POLLNVAL))) {
1072 if (pfd[2].revents & (POLLERR|POLLNVAL)) {
1073 BIO_printf(bio_err, "poll error");
1074 goto shut;
1075 }
1070 k = SSL_write(con, &(cbuf[cbuf_off]), 1076 k = SSL_write(con, &(cbuf[cbuf_off]),
1071 (unsigned int) cbuf_len); 1077 (unsigned int) cbuf_len);
1072 switch (SSL_get_error(con, k)) { 1078 switch (SSL_get_error(con, k)) {
@@ -1123,7 +1129,12 @@ re_start:
1123 ERR_print_errors(bio_err); 1129 ERR_print_errors(bio_err);
1124 goto shut; 1130 goto shut;
1125 } 1131 }
1126 } else if (!ssl_pending && FD_ISSET(fileno(stdout), &writefds)) { 1132 } else if (!ssl_pending &&
1133 (pfd[1].revents & (POLLOUT|POLLERR|POLLNVAL))) {
1134 if (pfd[1].revents & (POLLERR|POLLNVAL)) {
1135 BIO_printf(bio_err, "poll error");
1136 goto shut;
1137 }
1127 i = write(fileno(stdout), &(sbuf[sbuf_off]), sbuf_len); 1138 i = write(fileno(stdout), &(sbuf[sbuf_off]), sbuf_len);
1128 1139
1129 if (i <= 0) { 1140 if (i <= 0) {
@@ -1138,7 +1149,7 @@ re_start:
1138 read_ssl = 1; 1149 read_ssl = 1;
1139 write_tty = 0; 1150 write_tty = 0;
1140 } 1151 }
1141 } else if (ssl_pending || FD_ISSET(SSL_get_fd(con), &readfds)) { 1152 } else if (ssl_pending || (pfd[2].revents & (POLLIN|POLLHUP))) {
1142#ifdef RENEG 1153#ifdef RENEG
1143 { 1154 {
1144 static int iiii; 1155 static int iiii;
@@ -1188,7 +1199,11 @@ re_start:
1188 goto shut; 1199 goto shut;
1189 /* break; */ 1200 /* break; */
1190 } 1201 }
1191 } else if (FD_ISSET(fileno(stdin), &readfds)) { 1202 } else if (pfd[0].revents) {
1203 if (pfd[0].revents & (POLLERR|POLLNVAL)) {
1204 BIO_printf(bio_err, "poll error");
1205 goto shut;
1206 }
1192 if (crlf) { 1207 if (crlf) {
1193 int j, lf_num; 1208 int j, lf_num;
1194 1209