]> git.ipfire.org Git - thirdparty/gnutls.git/commitdiff
ktls: Do not return GNUTLS_E_INTERRUPTED/AGAIN from short writes
authorRichard W.M. Jones <rjones@redhat.com>
Fri, 10 Mar 2023 11:15:19 +0000 (11:15 +0000)
committerRichard W.M. Jones <rjones@redhat.com>
Fri, 10 Mar 2023 17:23:55 +0000 (17:23 +0000)
If sendmsg returns a short write, we end up going around the loop with
data_to_send being smaller.  However if sendmsg then returns -EAGAIN
or -EINTR then we return an error.  But we have "forgotten" that we
already sent some data.

This causes the caller to retry gnutls_record_send with the full
buffer (ie. with a buffer that has already been partially sent),
causing desynchronization.

Instead check if we sent some data in this case and return the number
of bytes sent.

Fixes: https://gitlab.com/gnutls/gnutls/-/issues/1470
Thanks: Dan Berrange for suggesting a fix
Signed-off-by: Richard W.M. Jones <rjones@redhat.com>
lib/system/ktls.c

index fd57a9c309fc66e1d486ecfc4a044f4dd4d71ec9..bb59fab7c0b58daf5e043144d8a376b0387125d2 100644 (file)
@@ -604,9 +604,17 @@ int _gnutls_ktls_send_control_msg(gnutls_session_t session,
                if (ret == -1) {
                        switch (errno) {
                        case EINTR:
-                               return GNUTLS_E_INTERRUPTED;
+                               if (data_to_send < data_size) {
+                                       return data_size - data_to_send;
+                               } else {
+                                       return GNUTLS_E_INTERRUPTED;
+                               }
                        case EAGAIN:
-                               return GNUTLS_E_AGAIN;
+                               if (data_to_send < data_size) {
+                                       return data_size - data_to_send;
+                               } else {
+                                       return GNUTLS_E_AGAIN;
+                               }
                        default:
                                return GNUTLS_E_PUSH_ERROR;
                        }