Don't use ssl3_write_pending in DTLS.

That function doesn't do anything useful for DTLS. It's meant for tracking the
rest of the record we've already committed to by writing half of one. But one
cannot write half a datagram, so DTLS never tracks this. Just call
ssl_write_buffer_flush straight and don't touch wpend_*.

Change-Id: Ibe191907d64c955c7cfeefba26f5c11ad5e4b939
Reviewed-on: https://boringssl-review.googlesource.com/6418
Reviewed-by: Adam Langley <agl@google.com>
diff --git a/ssl/d1_pkt.c b/ssl/d1_pkt.c
index a31dcc3..8cabdd4 100644
--- a/ssl/d1_pkt.c
+++ b/ssl/d1_pkt.c
@@ -512,8 +512,9 @@
 
 static int do_dtls1_write(SSL *s, int type, const uint8_t *buf,
                           unsigned int len, enum dtls1_use_epoch_t use_epoch) {
-  /* ssl3_write_pending drops the write if |BIO_write| fails in DTLS, so there
-   * is never pending data. */
+  /* There should never be a pending write buffer in DTLS. One can't write half
+   * a datagram, so the write buffer is always dropped in
+   * |ssl_write_buffer_flush|. */
   assert(!ssl_write_buffer_is_pending(s));
 
   /* If we have an alert to send, lets send it */
@@ -540,19 +541,16 @@
   if (!ssl_write_buffer_init(s, &out, max_out) ||
       !dtls_seal_record(s, out, &ciphertext_len, max_out, type, buf, len,
                         use_epoch)) {
+    ssl_write_buffer_clear(s);
     return -1;
   }
   ssl_write_buffer_set_len(s, ciphertext_len);
 
-  /* memorize arguments so that ssl3_write_pending can detect bad write retries
-   * later */
-  s->s3->wpend_tot = len;
-  s->s3->wpend_buf = buf;
-  s->s3->wpend_type = type;
-  s->s3->wpend_ret = len;
-
-  /* we now just need to write the buffer */
-  return ssl3_write_pending(s, type, buf, len);
+  int ret = ssl_write_buffer_flush(s);
+  if (ret <= 0) {
+    return ret;
+  }
+  return (int)len;
 }
 
 int dtls1_dispatch_alert(SSL *s) {
diff --git a/ssl/internal.h b/ssl/internal.h
index 76a31bf..842cf3f 100644
--- a/ssl/internal.h
+++ b/ssl/internal.h
@@ -1079,7 +1079,6 @@
 int dtls1_read_app_data(SSL *ssl, uint8_t *buf, int len, int peek);
 void dtls1_read_close_notify(SSL *ssl);
 int dtls1_read_bytes(SSL *s, int type, uint8_t *buf, int len, int peek);
-int ssl3_write_pending(SSL *s, int type, const uint8_t *buf, unsigned int len);
 void dtls1_set_message_header(SSL *s, uint8_t mt, unsigned long len,
                               unsigned short seq_num, unsigned long frag_off,
                               unsigned long frag_len);
diff --git a/ssl/s3_pkt.c b/ssl/s3_pkt.c
index 1cb2ac6..c50b315 100644
--- a/ssl/s3_pkt.c
+++ b/ssl/s3_pkt.c
@@ -249,6 +249,23 @@
   }
 }
 
+static int ssl3_write_pending(SSL *s, int type, const uint8_t *buf,
+                              unsigned int len) {
+  if (s->s3->wpend_tot > (int)len ||
+      (s->s3->wpend_buf != buf &&
+       !(s->mode & SSL_MODE_ACCEPT_MOVING_WRITE_BUFFER)) ||
+      s->s3->wpend_type != type) {
+    OPENSSL_PUT_ERROR(SSL, SSL_R_BAD_WRITE_RETRY);
+    return -1;
+  }
+
+  int ret = ssl_write_buffer_flush(s);
+  if (ret <= 0) {
+    return ret;
+  }
+  return s->s3->wpend_ret;
+}
+
 /* do_ssl3_write writes an SSL record of the given type. */
 static int do_ssl3_write(SSL *s, int type, const uint8_t *buf, unsigned len) {
   /* If there is still data from the previous record, flush it. */
@@ -298,22 +315,6 @@
   return ssl3_write_pending(s, type, buf, len);
 }
 
-int ssl3_write_pending(SSL *s, int type, const uint8_t *buf, unsigned int len) {
-  if (s->s3->wpend_tot > (int)len ||
-      (s->s3->wpend_buf != buf &&
-       !(s->mode & SSL_MODE_ACCEPT_MOVING_WRITE_BUFFER)) ||
-      s->s3->wpend_type != type) {
-    OPENSSL_PUT_ERROR(SSL, SSL_R_BAD_WRITE_RETRY);
-    return -1;
-  }
-
-  int ret = ssl_write_buffer_flush(s);
-  if (ret <= 0) {
-    return ret;
-  }
-  return s->s3->wpend_ret;
-}
-
 /* ssl3_expect_change_cipher_spec informs the record layer that a
  * ChangeCipherSpec record is required at this point. If a Handshake record is
  * received before ChangeCipherSpec, the connection will fail. Moreover, if