Coverage Report

Created: 2023-03-26 08:33

/src/gnutls/lib/record.c
Line
Count
Source (jump to first uncovered line)
1
/*
2
 * Copyright (C) 2000-2018 Free Software Foundation, Inc.
3
 * Copyright (C) 2012-2018 Nikos Mavrogiannopoulos
4
 * Copyright (C) 2018 Red Hat, Inc.
5
 *
6
 * Author: Nikos Mavrogiannopoulos
7
 *
8
 * This file is part of GnuTLS.
9
 *
10
 * The GnuTLS is free software; you can redistribute it and/or
11
 * modify it under the terms of the GNU Lesser General Public License
12
 * as published by the Free Software Foundation; either version 2.1 of
13
 * the License, or (at your option) any later version.
14
 *
15
 * This library is distributed in the hope that it will be useful, but
16
 * WITHOUT ANY WARRANTY; without even the implied warranty of
17
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
18
 * Lesser General Public License for more details.
19
 *
20
 * You should have received a copy of the GNU Lesser General Public License
21
 * along with this program.  If not, see <https://www.gnu.org/licenses/>
22
 *
23
 */
24
25
/* Functions that are record layer specific, are included in this file.
26
 */
27
28
/* allocate this many bytes more when encrypting or decrypting, to
29
 * compensate for broken backends such as cryptodev.
30
 */
31
0
#define CIPHER_SLACK_SIZE 32
32
33
#include "gnutls_int.h"
34
#include "errors.h"
35
#include "debug.h"
36
#include "cipher.h"
37
#include "buffers.h"
38
#include "mbuffers.h"
39
#include "handshake.h"
40
#include "hash_int.h"
41
#include "cipher_int.h"
42
#include "algorithms.h"
43
#include "db.h"
44
#include "auth.h"
45
#include "num.h"
46
#include "record.h"
47
#include "datum.h"
48
#include "constate.h"
49
#include "tls13/key_update.h"
50
#include <ext/heartbeat.h>
51
#include <state.h>
52
#include <dtls.h>
53
#include <dh.h>
54
#include <random.h>
55
#include <xsize.h>
56
#include "locks.h"
57
#include "system/ktls.h"
58
#include <intprops.h>
59
60
struct tls_record_st {
61
  uint16_t header_size;
62
  uint8_t version[2];
63
  uint64_t sequence;  /* DTLS */
64
  uint16_t length;
65
  uint16_t packet_size; /* header_size + length */
66
  content_type_t type;
67
  uint16_t epoch;   /* valid in DTLS only */
68
#ifdef ENABLE_SSL2
69
  unsigned v2:1;    /* whether an SSLv2 client hello */
70
#endif
71
  /* the data */
72
};
73
74
/**
75
 * gnutls_record_disable_padding:
76
 * @session: is a #gnutls_session_t type.
77
 *
78
 * Used to disabled padding in TLS 1.0 and above.  Normally you do not
79
 * need to use this function, but there are buggy clients that
80
 * complain if a server pads the encrypted data.  This of course will
81
 * disable protection against statistical attacks on the data.
82
 *
83
 * This function is defunct since 3.1.7. Random padding is disabled
84
 * by default unless requested using gnutls_record_send_range().
85
 *
86
 **/
87
void gnutls_record_disable_padding(gnutls_session_t session)
88
0
{
89
0
  return;
90
0
}
91
92
/**
93
 * gnutls_transport_set_ptr:
94
 * @session: is a #gnutls_session_t type.
95
 * @ptr: is the value.
96
 *
97
 * Used to set the first argument of the transport function (for push
98
 * and pull callbacks). In berkeley style sockets this function will set the
99
 * connection descriptor.
100
 *
101
 **/
102
void
103
gnutls_transport_set_ptr(gnutls_session_t session, gnutls_transport_ptr_t ptr)
104
0
{
105
0
  session->internals.transport_recv_ptr = ptr;
106
0
  session->internals.transport_send_ptr = ptr;
107
0
}
108
109
/**
110
 * gnutls_transport_set_ptr2:
111
 * @session: is a #gnutls_session_t type.
112
 * @recv_ptr: is the value for the pull function
113
 * @send_ptr: is the value for the push function
114
 *
115
 * Used to set the first argument of the transport function (for push
116
 * and pull callbacks). In berkeley style sockets this function will set the
117
 * connection descriptor.  With this function you can use two different
118
 * pointers for receiving and sending.
119
 **/
120
void
121
gnutls_transport_set_ptr2(gnutls_session_t session,
122
        gnutls_transport_ptr_t recv_ptr,
123
        gnutls_transport_ptr_t send_ptr)
124
0
{
125
0
  session->internals.transport_send_ptr = send_ptr;
126
0
  session->internals.transport_recv_ptr = recv_ptr;
127
0
}
128
129
/**
130
 * gnutls_transport_set_int2:
131
 * @session: is a #gnutls_session_t type.
132
 * @recv_fd: is socket descriptor for the pull function
133
 * @send_fd: is socket descriptor for the push function
134
 *
135
 * This function sets the first argument of the transport functions,
136
 * such as send() and recv() for the default callbacks using the
137
 * system's socket API. With this function you can set two different
138
 * descriptors for receiving and sending.
139
 *
140
 * This function is equivalent to calling gnutls_transport_set_ptr2()
141
 * with the descriptors, but requires no casts.
142
 *
143
 * Since: 3.1.9
144
 **/
145
void
146
gnutls_transport_set_int2(gnutls_session_t session, int recv_fd, int send_fd)
147
0
{
148
0
  session->internals.transport_send_ptr =
149
0
      (gnutls_transport_ptr_t) (long)send_fd;
150
0
  session->internals.transport_recv_ptr =
151
0
      (gnutls_transport_ptr_t) (long)recv_fd;
152
0
}
153
154
#if 0
155
/* this will be a macro */
156
/**
157
 * gnutls_transport_set_int:
158
 * @session: is a #gnutls_session_t type.
159
 * @fd: is the socket descriptor for the connection.
160
 *
161
 * This function sets the first argument of the transport function, such
162
 * as send() and recv() for the default callbacks using the
163
 * system's socket API.
164
 *
165
 * This function is equivalent to calling gnutls_transport_set_ptr()
166
 * with the descriptor, but requires no casts.
167
 *
168
 * Since: 3.1.9
169
 *
170
 **/
171
void gnutls_transport_set_int(gnutls_session_t session, int fd)
172
{
173
  session->internals.transport_recv_ptr =
174
      (gnutls_transport_ptr_t) (long)fd;
175
  session->internals.transport_send_ptr =
176
      (gnutls_transport_ptr_t) (long)fd;
177
}
178
#endif
179
180
/**
181
 * gnutls_transport_get_ptr:
182
 * @session: is a #gnutls_session_t type.
183
 *
184
 * Used to get the first argument of the transport function (like
185
 * PUSH and PULL).  This must have been set using
186
 * gnutls_transport_set_ptr().
187
 *
188
 * Returns: The first argument of the transport function.
189
 **/
190
gnutls_transport_ptr_t gnutls_transport_get_ptr(gnutls_session_t session)
191
0
{
192
0
  return session->internals.transport_recv_ptr;
193
0
}
194
195
/**
196
 * gnutls_transport_get_ptr2:
197
 * @session: is a #gnutls_session_t type.
198
 * @recv_ptr: will hold the value for the pull function
199
 * @send_ptr: will hold the value for the push function
200
 *
201
 * Used to get the arguments of the transport functions (like PUSH
202
 * and PULL).  These should have been set using
203
 * gnutls_transport_set_ptr2().
204
 **/
205
void
206
gnutls_transport_get_ptr2(gnutls_session_t session,
207
        gnutls_transport_ptr_t * recv_ptr,
208
        gnutls_transport_ptr_t * send_ptr)
209
0
{
210
211
0
  *recv_ptr = session->internals.transport_recv_ptr;
212
0
  *send_ptr = session->internals.transport_send_ptr;
213
0
}
214
215
/**
216
 * gnutls_transport_get_int2:
217
 * @session: is a #gnutls_session_t type.
218
 * @recv_int: will hold the value for the pull function
219
 * @send_int: will hold the value for the push function
220
 *
221
 * Used to get the arguments of the transport functions (like PUSH
222
 * and PULL).  These should have been set using
223
 * gnutls_transport_set_int2().
224
 *
225
 * Since: 3.1.9
226
 **/
227
void
228
gnutls_transport_get_int2(gnutls_session_t session,
229
        int *recv_int, int *send_int)
230
0
{
231
232
0
  *recv_int = (long)session->internals.transport_recv_ptr;
233
0
  *send_int = (long)session->internals.transport_send_ptr;
234
0
}
235
236
/**
237
 * gnutls_transport_get_int:
238
 * @session: is a #gnutls_session_t type.
239
 *
240
 * Used to get the first argument of the transport function (like
241
 * PUSH and PULL).  This must have been set using
242
 * gnutls_transport_set_int().
243
 *
244
 * Returns: The first argument of the transport function.
245
 *
246
 * Since: 3.1.9
247
 **/
248
int gnutls_transport_get_int(gnutls_session_t session)
249
0
{
250
0
  return (long)session->internals.transport_recv_ptr;
251
0
}
252
253
/**
254
 * gnutls_bye:
255
 * @session: is a #gnutls_session_t type.
256
 * @how: is an integer
257
 *
258
 * Terminates the current TLS/SSL connection. The connection should
259
 * have been initiated using gnutls_handshake().  @how should be one
260
 * of %GNUTLS_SHUT_RDWR, %GNUTLS_SHUT_WR.
261
 *
262
 * In case of %GNUTLS_SHUT_RDWR the TLS session gets
263
 * terminated and further receives and sends will be disallowed.  If
264
 * the return value is zero you may continue using the underlying
265
 * transport layer. %GNUTLS_SHUT_RDWR sends an alert containing a close
266
 * request and waits for the peer to reply with the same message.
267
 *
268
 * In case of %GNUTLS_SHUT_WR the TLS session gets terminated
269
 * and further sends will be disallowed. In order to reuse the
270
 * connection you should wait for an EOF from the peer.
271
 * %GNUTLS_SHUT_WR sends an alert containing a close request.
272
 *
273
 * Note that not all implementations will properly terminate a TLS
274
 * connection.  Some of them, usually for performance reasons, will
275
 * terminate only the underlying transport layer, and thus not
276
 * distinguishing between a malicious party prematurely terminating
277
 * the connection and normal termination.
278
 *
279
 * This function may also return %GNUTLS_E_AGAIN or
280
 * %GNUTLS_E_INTERRUPTED; cf.  gnutls_record_get_direction().
281
 *
282
 * Returns: %GNUTLS_E_SUCCESS on success, or an error code, see
283
 *   function documentation for entire semantics.
284
 **/
285
int gnutls_bye(gnutls_session_t session, gnutls_close_request_t how)
286
0
{
287
0
  int ret = 0;
288
289
0
  switch (BYE_STATE) {
290
0
  case BYE_STATE0:
291
0
    if (!IS_KTLS_ENABLED(session, GNUTLS_KTLS_SEND))
292
0
      ret = _gnutls_io_write_flush(session);
293
0
    BYE_STATE = BYE_STATE0;
294
0
    if (ret < 0) {
295
0
      gnutls_assert();
296
0
      return ret;
297
0
    }
298
0
    FALLTHROUGH;
299
0
  case BYE_STATE1:
300
0
    ret = gnutls_alert_send(session, GNUTLS_AL_WARNING,
301
0
          GNUTLS_A_CLOSE_NOTIFY);
302
0
    BYE_STATE = BYE_STATE1;
303
0
    if (ret < 0) {
304
0
      gnutls_assert();
305
0
      return ret;
306
0
    }
307
0
    FALLTHROUGH;
308
0
  case BYE_STATE2:
309
0
    BYE_STATE = BYE_STATE2;
310
0
    if (how == GNUTLS_SHUT_RDWR) {
311
0
      if (IS_KTLS_ENABLED(session, GNUTLS_KTLS_SEND)) {
312
0
        do {
313
0
          ret = _gnutls_ktls_recv_int(session,
314
0
                    GNUTLS_ALERT,
315
0
                    NULL, 0);
316
0
        }
317
0
        while (ret == GNUTLS_E_GOT_APPLICATION_DATA);
318
0
      } else {
319
0
        do {
320
0
          ret =
321
0
              _gnutls_recv_int(session,
322
0
                   GNUTLS_ALERT, NULL,
323
0
                   0, NULL,
324
0
                   session->internals.
325
0
                   record_timeout_ms);
326
0
        }
327
0
        while (ret == GNUTLS_E_GOT_APPLICATION_DATA);
328
0
      }
329
330
0
      if (ret >= 0)
331
0
        session->internals.may_not_read = 1;
332
333
0
      if (ret < 0) {
334
0
        gnutls_assert();
335
0
        return ret;
336
0
      }
337
0
    }
338
0
    BYE_STATE = BYE_STATE2;
339
340
0
    break;
341
0
  default:
342
0
    gnutls_assert();
343
0
    return GNUTLS_E_INTERNAL_ERROR;
344
0
  }
345
346
0
  BYE_STATE = BYE_STATE0;
347
348
0
  session->internals.may_not_write = 1;
349
0
  return 0;
350
0
}
351
352
inline static void session_unresumable(gnutls_session_t session)
353
0
{
354
0
  session->internals.resumable = false;
355
0
}
356
357
/* returns 0 if session is valid
358
 */
359
inline static int session_is_valid(gnutls_session_t session)
360
0
{
361
0
  if (session->internals.invalid_connection != 0)
362
0
    return GNUTLS_E_INVALID_SESSION;
363
364
0
  return 0;
365
0
}
366
367
/* Copies the record version into the headers. The
368
 * version must have 2 bytes at least.
369
 */
370
inline static int
371
copy_record_version(gnutls_session_t session,
372
        gnutls_handshake_description_t htype, uint8_t version[2])
373
0
{
374
0
  const version_entry_st *lver;
375
376
0
  lver = get_version(session);
377
0
  if (session->internals.initial_negotiation_completed ||
378
0
      htype != GNUTLS_HANDSHAKE_CLIENT_HELLO ||
379
0
      (session->internals.hsk_flags & HSK_HRR_RECEIVED) ||
380
0
      session->internals.default_record_version[0] == 0) {
381
382
0
    if (unlikely(lver == NULL))
383
0
      return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
384
385
0
    if (lver->tls13_sem) {
386
0
      version[0] = 0x03;
387
0
      version[1] = 0x03;
388
0
    } else {
389
0
      version[0] = lver->major;
390
0
      version[1] = lver->minor;
391
0
    }
392
0
  } else {
393
0
    version[0] = session->internals.default_record_version[0];
394
0
    version[1] = session->internals.default_record_version[1];
395
0
  }
396
397
0
  return 0;
398
0
}
399
400
/* Increments the sequence value
401
 */
402
inline static int sequence_increment(gnutls_session_t session, uint64_t * value)
403
0
{
404
0
  uint64_t snmax = UINT64_C(0xffffffffffffffff);
405
406
0
  if (IS_DTLS(session)) {
407
0
    uint64_t mask;
408
409
0
    snmax = UINT64_C(0xffffffffffff);
410
0
    mask = snmax;
411
412
0
    if ((*value & mask) == snmax)
413
0
      return -1;
414
415
0
    *value = ((*value & mask) + 1) | (*value & ~mask);
416
0
  } else {
417
0
    if (*value == snmax)
418
0
      return -1;
419
420
0
    (*value)++;
421
0
  }
422
423
0
  return 0;
424
0
}
425
426
/* This function behaves exactly like write(). The only difference is
427
 * that it accepts, the gnutls_session_t and the content_type_t of data to
428
 * send (if called by the user the Content is specific)
429
 * It is intended to transfer data, under the current session.
430
 *
431
 * @type: The content type to send
432
 * @htype: If this is a handshake message then the handshake type
433
 * @epoch_rel: %EPOCH_READ_* or %EPOCH_WRITE_*
434
 * @data: the data to be sent
435
 * @data_size: the size of the @data
436
 * @min_pad: the minimum required padding
437
 * @mflags: zero or %MBUFFER_FLUSH
438
 *
439
 * Oct 30 2001: Removed capability to send data more than MAX_RECORD_SIZE.
440
 * This makes the function much easier to read, and more error resistant
441
 * (there were cases were the old function could mess everything up).
442
 * --nmav
443
 *
444
 * This function may accept a NULL pointer for data, and 0 for size, if
445
 * and only if the previous send was interrupted for some reason.
446
 *
447
 */
448
ssize_t
449
_gnutls_send_tlen_int(gnutls_session_t session, content_type_t type,
450
          gnutls_handshake_description_t htype,
451
          unsigned int epoch_rel, const void *_data,
452
          size_t data_size, size_t min_pad, unsigned int mflags)
453
0
{
454
0
  mbuffer_st *bufel;
455
0
  ssize_t cipher_size;
456
0
  int retval, ret;
457
0
  int send_data_size;
458
0
  uint8_t *headers;
459
0
  int header_size;
460
0
  const uint8_t *data = _data;
461
0
  record_parameters_st *record_params;
462
0
  size_t max_send_size;
463
0
  record_state_st *record_state;
464
0
  const version_entry_st *vers = get_version(session);
465
466
0
  ret = _gnutls_epoch_get(session, epoch_rel, &record_params);
467
0
  if (ret < 0)
468
0
    return gnutls_assert_val(ret);
469
470
  /* Safeguard against processing data with an incomplete cipher state. */
471
0
  if (!record_params->initialized)
472
0
    return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
473
474
0
  record_state = &record_params->write;
475
476
  /* Do not allow null pointer if the send buffer is empty.
477
   * If the previous send was interrupted then a null pointer is
478
   * ok, and means to resume.
479
   */
480
0
  if (session->internals.record_send_buffer.byte_length == 0 &&
481
0
      (data_size == 0 && _data == NULL)) {
482
0
    gnutls_assert();
483
0
    return GNUTLS_E_INVALID_REQUEST;
484
0
  }
485
486
0
  if (type != GNUTLS_ALERT) /* alert messages are sent anyway */
487
0
    if (session_is_valid(session)
488
0
        || session->internals.may_not_write != 0) {
489
0
      gnutls_assert();
490
0
      return GNUTLS_E_INVALID_SESSION;
491
0
    }
492
493
0
  max_send_size = max_record_send_size(session);
494
495
0
  if (data_size > max_send_size) {
496
0
    if (IS_DTLS(session))
497
0
      return gnutls_assert_val(GNUTLS_E_LARGE_PACKET);
498
499
0
    send_data_size = max_send_size;
500
0
  } else
501
0
    send_data_size = data_size;
502
503
  /* Only encrypt if we don't have data to send
504
   * from the previous run. - probably interrupted.
505
   */
506
0
  if (mflags != 0
507
0
      && session->internals.record_send_buffer.byte_length > 0) {
508
0
    ret = _gnutls_io_write_flush(session);
509
0
    if (ret > 0)
510
0
      cipher_size = ret;
511
0
    else
512
0
      cipher_size = 0;
513
514
0
    retval = session->internals.record_send_buffer_user_size;
515
0
  } else {
516
0
    if (unlikely((send_data_size == 0 && min_pad == 0)))
517
0
      return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
518
519
    /* now proceed to packet encryption
520
     */
521
0
    cipher_size = max_record_send_size(session) +
522
0
        MAX_RECORD_SEND_OVERHEAD(session);
523
524
0
    bufel = _mbuffer_alloc_align16(cipher_size + CIPHER_SLACK_SIZE,
525
0
                 get_total_headers2(session,
526
0
                  record_params));
527
0
    if (bufel == NULL)
528
0
      return gnutls_assert_val(GNUTLS_E_MEMORY_ERROR);
529
530
0
    headers = _mbuffer_get_uhead_ptr(bufel);
531
0
    if (vers->tls13_sem
532
0
        && record_params->cipher->id != GNUTLS_CIPHER_NULL)
533
0
      headers[0] = GNUTLS_APPLICATION_DATA;
534
0
    else
535
0
      headers[0] = type;
536
537
    /* Use the default record version, if it is
538
     * set. */
539
0
    ret = copy_record_version(session, htype, &headers[1]);
540
0
    if (ret < 0)
541
0
      return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
542
543
    /* Adjust header length and add sequence for DTLS */
544
0
    if (IS_DTLS(session))
545
0
      _gnutls_write_uint64(record_state->sequence_number,
546
0
               &headers[3]);
547
548
0
    _gnutls_record_log
549
0
        ("REC[%p]: Preparing Packet %s(%d) with length: %d and min pad: %d\n",
550
0
         session, _gnutls_packet2str(type), type,
551
0
         (int)data_size, (int)min_pad);
552
553
0
    header_size = RECORD_HEADER_SIZE(session);
554
0
    _mbuffer_set_udata_size(bufel, cipher_size);
555
0
    _mbuffer_set_uhead_size(bufel, header_size);
556
557
0
    ret =
558
0
        _gnutls_encrypt(session,
559
0
            data, send_data_size, min_pad,
560
0
            bufel, type, record_params);
561
0
    if (ret <= 0) {
562
0
      gnutls_assert();
563
0
      if (ret == 0)
564
0
        ret = GNUTLS_E_ENCRYPTION_FAILED;
565
0
      gnutls_free(bufel);
566
0
      return ret; /* error */
567
0
    }
568
569
0
    cipher_size = _mbuffer_get_udata_size(bufel);
570
0
    retval = send_data_size;
571
0
    session->internals.record_send_buffer_user_size =
572
0
        send_data_size;
573
574
    /* increase sequence number
575
     */
576
0
    if (sequence_increment
577
0
        (session, &record_state->sequence_number) != 0) {
578
0
      session_invalidate(session);
579
0
      gnutls_free(bufel);
580
0
      return gnutls_assert_val(GNUTLS_E_RECORD_LIMIT_REACHED);
581
0
    }
582
583
0
    ret = _gnutls_io_write_buffered(session, bufel, mflags);
584
0
  }
585
586
0
  if (ret != cipher_size) {
587
    /* If we have sent any data then just return
588
     * the error value. Do not invalidate the session.
589
     */
590
0
    if (ret < 0 && gnutls_error_is_fatal(ret) == 0)
591
0
      return gnutls_assert_val(ret);
592
593
0
    if (ret > 0)
594
0
      ret = gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
595
596
0
    session_unresumable(session);
597
0
    session->internals.may_not_write = 1;
598
0
    return gnutls_assert_val(ret);
599
0
  }
600
601
0
  session->internals.record_send_buffer_user_size = 0;
602
603
0
  _gnutls_record_log
604
0
      ("REC[%p]: Sent Packet[%ld] %s(%d) in epoch %d and length: %d\n",
605
0
       session, (unsigned long)(record_state->sequence_number),
606
0
       _gnutls_packet2str(type), type, (int)record_params->epoch,
607
0
       (int)cipher_size);
608
609
0
  if (vers->tls13_sem
610
0
      && !(session->internals.flags & GNUTLS_NO_AUTO_REKEY)
611
0
      && !(record_params->cipher->flags & GNUTLS_CIPHER_FLAG_NO_REKEY)) {
612
0
    if (unlikely
613
0
        ((record_state->sequence_number & UINT64_C(0xffffff)) ==
614
0
         UINT64_C(0xfffffd))) {
615
      /* After we have sent 2^24 messages, mark the session
616
       * as needing a key update. */
617
0
      session->internals.rsend_state =
618
0
          RECORD_SEND_KEY_UPDATE_1;
619
0
    }
620
0
  }
621
622
0
  return retval;
623
0
}
624
625
inline static int
626
check_recv_type(gnutls_session_t session, content_type_t recv_type)
627
0
{
628
0
  switch (recv_type) {
629
0
  case GNUTLS_CHANGE_CIPHER_SPEC:
630
0
  case GNUTLS_ALERT:
631
0
  case GNUTLS_HANDSHAKE:
632
0
  case GNUTLS_HEARTBEAT:
633
0
  case GNUTLS_APPLICATION_DATA:
634
0
    return 0;
635
0
  default:
636
0
    gnutls_assert();
637
0
    _gnutls_audit_log(session,
638
0
          "Received record packet of unknown type %u\n",
639
0
          (unsigned int)recv_type);
640
0
    return GNUTLS_E_UNEXPECTED_PACKET;
641
0
  }
642
643
0
}
644
645
/* Checks if there are pending data in the record buffers. If there are
646
 * then it copies the data.
647
 */
648
static int
649
get_data_from_buffers(gnutls_session_t session, content_type_t type,
650
          uint8_t * data, int data_size, void *seq)
651
0
{
652
0
  if ((type == GNUTLS_APPLICATION_DATA ||
653
0
       type == GNUTLS_HANDSHAKE || type == GNUTLS_CHANGE_CIPHER_SPEC)
654
0
      && _gnutls_record_buffer_get_size(session) > 0) {
655
0
    int ret;
656
0
    ret =
657
0
        _gnutls_record_buffer_get(type, session, data,
658
0
                data_size, seq);
659
0
    if (ret < 0) {
660
0
      if (IS_DTLS(session)) {
661
0
        if (ret == GNUTLS_E_UNEXPECTED_PACKET) {
662
0
          ret = GNUTLS_E_AGAIN;
663
0
        }
664
0
      }
665
0
      gnutls_assert();
666
0
      return ret;
667
0
    }
668
669
0
    return ret;
670
0
  }
671
672
0
  return 0;
673
0
}
674
675
/* Checks and retrieves any pending data in the application data record buffers.
676
 */
677
static int
678
get_packet_from_buffers(gnutls_session_t session, content_type_t type,
679
      gnutls_packet_t * packet)
680
0
{
681
0
  if (_gnutls_record_buffer_get_size(session) > 0) {
682
0
    int ret;
683
0
    ret = _gnutls_record_buffer_get_packet(type, session, packet);
684
0
    if (ret < 0) {
685
0
      if (IS_DTLS(session)) {
686
0
        if (ret == GNUTLS_E_UNEXPECTED_PACKET) {
687
0
          ret = GNUTLS_E_AGAIN;
688
0
        }
689
0
      }
690
0
      gnutls_assert();
691
0
      return ret;
692
0
    }
693
694
0
    return ret;
695
0
  }
696
697
0
  *packet = NULL;
698
0
  return 0;
699
0
}
700
701
/* Here we check if the advertized version is the one we
702
 * negotiated in the handshake.
703
 */
704
inline static int
705
record_check_version(gnutls_session_t session,
706
         gnutls_handshake_description_t htype, uint8_t version[2])
707
0
{
708
0
  const version_entry_st *vers = get_version(session);
709
0
  int diff = 0;
710
711
0
  if (vers->tls13_sem) {
712
    /* TLS 1.3 requires version to be 0x0303 */
713
0
    if (version[0] != 0x03 || version[1] != 0x03)
714
0
      diff = 1;
715
0
  } else {
716
0
    if (vers->major != version[0] || vers->minor != version[1])
717
0
      diff = 1;
718
0
  }
719
720
0
  if (!IS_DTLS(session)) {
721
0
    if (htype == GNUTLS_HANDSHAKE_CLIENT_HELLO ||
722
0
        htype == GNUTLS_HANDSHAKE_HELLO_RETRY_REQUEST ||
723
0
        htype == GNUTLS_HANDSHAKE_SERVER_HELLO) {
724
0
      if (version[0] != 3) {
725
0
        gnutls_assert();
726
0
        _gnutls_record_log
727
0
            ("REC[%p]: INVALID VERSION PACKET: (%d) %d.%d\n",
728
0
             session, htype, version[0], version[1]);
729
0
        return GNUTLS_E_UNSUPPORTED_VERSION_PACKET;
730
0
      }
731
0
    } else if (diff != 0) {
732
      /* Reject record packets that have a different version than the
733
       * one negotiated. Note that this version is not protected by any
734
       * mac. I don't really think that this check serves any purpose.
735
       */
736
0
      gnutls_assert();
737
0
      _gnutls_record_log
738
0
          ("REC[%p]: INVALID VERSION PACKET: (%d) %d.%d\n",
739
0
           session, htype, version[0], version[1]);
740
741
0
      return GNUTLS_E_UNSUPPORTED_VERSION_PACKET;
742
0
    }
743
0
  } else {   /* DTLS */
744
745
    /* In DTLS the only information we have here is whether we
746
     * expect a handshake message or not.
747
     */
748
0
    if (htype == (gnutls_handshake_description_t) - 1) {
749
0
      if (diff) {
750
        /* Reject record packets that have a different version than the
751
         * one negotiated. Note that this version is not protected by any
752
         * mac. I don't really think that this check serves any purpose.
753
         */
754
0
        gnutls_assert();
755
0
        _gnutls_record_log
756
0
            ("REC[%p]: INVALID VERSION PACKET: (%d) %d.%d\n",
757
0
             session, htype, version[0], version[1]);
758
759
0
        return GNUTLS_E_UNSUPPORTED_VERSION_PACKET;
760
0
      }
761
0
    } else if (vers->id > GNUTLS_DTLS1_0 && version[0] > 254) {
762
0
      gnutls_assert();
763
0
      _gnutls_record_log
764
0
          ("REC[%p]: INVALID DTLS VERSION PACKET: (%d) %d.%d\n",
765
0
           session, htype, version[0], version[1]);
766
0
      return GNUTLS_E_UNSUPPORTED_VERSION_PACKET;
767
0
    } else if (vers->id == GNUTLS_DTLS0_9 && version[0] > 1) {
768
0
      gnutls_assert();
769
0
      _gnutls_record_log
770
0
          ("REC[%p]: INVALID DTLS VERSION PACKET: (%d) %d.%d\n",
771
0
           session, htype, version[0], version[1]);
772
0
      return GNUTLS_E_UNSUPPORTED_VERSION_PACKET;
773
0
    }
774
0
  }
775
776
0
  return 0;
777
0
}
778
779
static int
780
recv_hello_request(gnutls_session_t session, void *data, uint32_t data_size)
781
0
{
782
0
  uint8_t type;
783
784
0
  if (session->security_parameters.entity == GNUTLS_SERVER)
785
0
    return gnutls_assert_val(GNUTLS_E_UNEXPECTED_PACKET);
786
787
0
  if (data_size < 1)
788
0
    return gnutls_assert_val(GNUTLS_E_UNEXPECTED_PACKET_LENGTH);
789
790
0
  if (session->internals.handshake_in_progress)
791
0
    return gnutls_assert_val(GNUTLS_E_UNEXPECTED_PACKET);
792
793
0
  type = ((uint8_t *) data)[0];
794
0
  if (type == GNUTLS_HANDSHAKE_HELLO_REQUEST) {
795
0
    if (IS_DTLS(session))
796
0
      session->internals.dtls.hsk_read_seq++;
797
0
    if (session->internals.flags & GNUTLS_AUTO_REAUTH) {
798
0
      session->internals.recv_state = RECV_STATE_REHANDSHAKE;
799
0
      return GNUTLS_E_AGAIN;
800
0
    } else {
801
0
      return GNUTLS_E_REHANDSHAKE;
802
0
    }
803
0
  } else {
804
0
    gnutls_assert();
805
0
    return GNUTLS_E_UNEXPECTED_PACKET;
806
0
  }
807
0
}
808
809
/* This function will check if the received record type is
810
 * the one we actually expect and adds it to the proper
811
 * buffer. The bufel will be deinitialized after calling
812
 * this function, even if it fails.
813
 */
814
static int
815
record_add_to_buffers(gnutls_session_t session,
816
          struct tls_record_st *recv, content_type_t type,
817
          gnutls_handshake_description_t htype,
818
          uint64_t seq, mbuffer_st * bufel)
819
0
{
820
821
0
  int ret;
822
0
  const version_entry_st *ver = get_version(session);
823
824
0
  if ((recv->type == type)
825
0
      && (type == GNUTLS_APPLICATION_DATA ||
826
0
    type == GNUTLS_CHANGE_CIPHER_SPEC ||
827
0
    type == GNUTLS_HANDSHAKE)) {
828
0
    if (bufel->msg.size == 0) {
829
0
      if (type == GNUTLS_APPLICATION_DATA) {
830
        /* this is needed to distinguish an empty
831
         * message and EOF */
832
0
        ret = GNUTLS_E_AGAIN;
833
0
        goto cleanup;
834
0
      } else {
835
0
        ret =
836
0
            gnutls_assert_val
837
0
            (GNUTLS_E_UNEXPECTED_PACKET);
838
0
        goto unexpected_packet;
839
0
      }
840
0
    }
841
842
    /* application data cannot be inserted between (async) handshake
843
     * messages */
844
0
    if (type == GNUTLS_APPLICATION_DATA &&
845
0
        (session->internals.handshake_recv_buffer_size != 0 ||
846
0
         session->internals.handshake_header_recv_buffer.length !=
847
0
         0)) {
848
0
      ret = gnutls_assert_val(GNUTLS_E_UNEXPECTED_PACKET);
849
0
      goto unexpected_packet;
850
0
    }
851
852
    /* if the CCS has value other than 1 abort the connection,
853
     * unless old DTLS is negotiated, where CCS includes a sequence
854
     * number */
855
0
    if (type == GNUTLS_CHANGE_CIPHER_SPEC &&
856
0
        !(ver && ver->id == GNUTLS_DTLS0_9) &&
857
0
        (bufel->msg.size != 1 || bufel->msg.data[0] != 1)) {
858
0
      ret = gnutls_assert_val(GNUTLS_E_UNEXPECTED_PACKET);
859
0
      goto unexpected_packet;
860
0
    }
861
862
0
    _gnutls_record_buffer_put(session, type, seq, bufel);
863
864
    /* if we received application data as expected then we
865
     * deactivate the async timer */
866
0
    _dtls_async_timer_delete(session);
867
0
  } else {
868
    /* if the expected type is different than the received
869
     */
870
0
    switch (recv->type) {
871
0
    case GNUTLS_ALERT:
872
0
      if (bufel->msg.size < 2) {
873
0
        ret =
874
0
            gnutls_assert_val
875
0
            (GNUTLS_E_UNEXPECTED_PACKET);
876
0
        goto unexpected_packet;
877
0
      }
878
879
0
      _gnutls_record_log
880
0
          ("REC[%p]: Alert[%d|%d] - %s - was received\n",
881
0
           session, bufel->msg.data[0],
882
0
           bufel->msg.data[1],
883
0
           gnutls_alert_get_name((int)bufel->msg.data[1]));
884
885
0
      if (!session->internals.initial_negotiation_completed && session->internals.handshake_in_progress && STATE == STATE0) { /* handshake hasn't started */
886
0
        ret =
887
0
            gnutls_assert_val
888
0
            (GNUTLS_E_UNEXPECTED_PACKET);
889
0
        goto unexpected_packet;
890
0
      }
891
892
0
      session->internals.last_alert = bufel->msg.data[1];
893
894
      /* if close notify is received and
895
       * the alert is not fatal
896
       */
897
0
      if (bufel->msg.data[1] == GNUTLS_A_CLOSE_NOTIFY
898
0
          && bufel->msg.data[0] != GNUTLS_AL_FATAL) {
899
        /* If we have been expecting for an alert do
900
         */
901
0
        session->internals.read_eof = 1;
902
0
        ret = GNUTLS_E_SESSION_EOF;
903
0
        goto cleanup;
904
0
      } else {
905
        /* if the alert is FATAL or WARNING
906
         * return the appropriate message
907
         */
908
0
        gnutls_assert();
909
0
        ret = GNUTLS_E_WARNING_ALERT_RECEIVED;
910
0
        if ((ver && ver->tls13_sem)
911
0
            || bufel->msg.data[0] == GNUTLS_AL_FATAL) {
912
0
          session_unresumable(session);
913
0
          session_invalidate(session);
914
0
          ret =
915
0
              gnutls_assert_val
916
0
              (GNUTLS_E_FATAL_ALERT_RECEIVED);
917
0
        }
918
0
        goto cleanup;
919
0
      }
920
0
      break;
921
922
0
    case GNUTLS_CHANGE_CIPHER_SPEC:
923
0
      if (!(IS_DTLS(session))) {
924
0
        ret =
925
0
            gnutls_assert_val
926
0
            (GNUTLS_E_UNEXPECTED_PACKET);
927
0
        goto cleanup;
928
0
      }
929
930
      /* if the CCS has value other than 1 abort the
931
       * connection, unless old DTLS is negotiated, where CCS
932
       * includes a sequence number */
933
0
      if (!(ver && ver->id == GNUTLS_DTLS0_9) &&
934
0
          (bufel->msg.size != 1 || bufel->msg.data[0] != 1)) {
935
0
        ret =
936
0
            gnutls_assert_val
937
0
            (GNUTLS_E_UNEXPECTED_PACKET);
938
0
        goto unexpected_packet;
939
0
      }
940
941
0
      _gnutls_record_buffer_put(session, recv->type, seq,
942
0
              bufel);
943
944
0
      break;
945
946
#ifdef ENABLE_HEARTBEAT
947
    case GNUTLS_HEARTBEAT:
948
      ret = _gnutls_heartbeat_handle(session, bufel);
949
      goto cleanup;
950
#endif
951
952
0
    case GNUTLS_APPLICATION_DATA:
953
0
      if (session->internals.initial_negotiation_completed ==
954
0
          0) {
955
0
        ret =
956
0
            gnutls_assert_val
957
0
            (GNUTLS_E_UNEXPECTED_PACKET);
958
0
        goto unexpected_packet;
959
0
      }
960
961
      /* In TLS1.3 post-handshake authentication allow application
962
       * data error code. */
963
0
      if ((ver && ver->tls13_sem) && type == GNUTLS_HANDSHAKE
964
0
          && htype == GNUTLS_HANDSHAKE_CERTIFICATE_PKT
965
0
          && session->
966
0
          internals.initial_negotiation_completed) {
967
0
        _gnutls_record_buffer_put(session, recv->type,
968
0
                seq, bufel);
969
0
        return
970
0
            gnutls_assert_val
971
0
            (GNUTLS_E_GOT_APPLICATION_DATA);
972
0
      }
973
974
      /* The got_application data is only returned
975
       * if expecting client hello (for rehandshake
976
       * reasons). Otherwise it is an unexpected packet
977
       */
978
0
      if (type == GNUTLS_ALERT
979
0
          || ((htype == GNUTLS_HANDSHAKE_SERVER_HELLO ||
980
0
         htype == GNUTLS_HANDSHAKE_CLIENT_HELLO ||
981
0
         htype == GNUTLS_HANDSHAKE_HELLO_RETRY_REQUEST)
982
0
        && type == GNUTLS_HANDSHAKE)) {
983
        /* even if data is unexpected put it into the buffer */
984
0
        _gnutls_record_buffer_put(session, recv->type,
985
0
                seq, bufel);
986
0
        return
987
0
            gnutls_assert_val
988
0
            (GNUTLS_E_GOT_APPLICATION_DATA);
989
0
      } else {
990
0
        ret =
991
0
            gnutls_assert_val
992
0
            (GNUTLS_E_UNEXPECTED_PACKET);
993
0
        goto unexpected_packet;
994
0
      }
995
996
0
      break;
997
998
0
    case GNUTLS_HANDSHAKE:
999
      /* In DTLS we might receive a handshake replay from the peer to indicate
1000
       * the our last TLS handshake messages were not received.
1001
       */
1002
0
      if (IS_DTLS(session)) {
1003
0
        if (type == GNUTLS_CHANGE_CIPHER_SPEC) {
1004
0
          ret =
1005
0
              gnutls_assert_val
1006
0
              (GNUTLS_E_UNEXPECTED_PACKET);
1007
0
          goto unexpected_packet;
1008
0
        }
1009
1010
0
        if (_dtls_is_async(session)
1011
0
            && _dtls_async_timer_active(session)) {
1012
0
          if (session->security_parameters.
1013
0
              entity == GNUTLS_SERVER
1014
0
              && bufel->htype ==
1015
0
              GNUTLS_HANDSHAKE_CLIENT_HELLO) {
1016
            /* client requested rehandshake. Delete the timer */
1017
0
            _dtls_async_timer_delete
1018
0
                (session);
1019
0
          } else {
1020
0
            session->internals.recv_state =
1021
0
                RECV_STATE_DTLS_RETRANSMIT;
1022
0
            ret = _dtls_retransmit(session);
1023
0
            if (ret == 0) {
1024
0
              session->internals.
1025
0
                  recv_state =
1026
0
                  RECV_STATE_0;
1027
0
              ret =
1028
0
                  gnutls_assert_val
1029
0
                  (GNUTLS_E_AGAIN);
1030
0
              goto unexpected_packet;
1031
0
            }
1032
0
            goto cleanup;
1033
0
          }
1034
0
        }
1035
0
      }
1036
1037
      /* retrieve async handshake messages */
1038
0
      if (ver && ver->tls13_sem) {
1039
0
        _gnutls_record_buffer_put(session, recv->type,
1040
0
                seq, bufel);
1041
1042
0
        ret = _gnutls13_recv_async_handshake(session);
1043
0
        if (ret < 0)
1044
0
          return gnutls_assert_val(ret);
1045
1046
        /* bufel is now accounted */
1047
0
        return GNUTLS_E_AGAIN;
1048
0
      }
1049
1050
      /* This is legal if HELLO_REQUEST is received - and we are a client.
1051
       * If we are a server, a client may initiate a renegotiation at any time.
1052
       */
1053
0
      if (session->security_parameters.entity ==
1054
0
          GNUTLS_SERVER
1055
0
          && session->internals.handshake_in_progress == 0
1056
0
          && bufel->htype == GNUTLS_HANDSHAKE_CLIENT_HELLO) {
1057
0
        gnutls_assert();
1058
0
        _gnutls_record_buffer_put(session,
1059
0
                recv->type,
1060
0
                seq, bufel);
1061
0
        return GNUTLS_E_REHANDSHAKE;
1062
0
      }
1063
1064
      /* If we are already in a handshake then a Hello
1065
       * Request is illegal. But here we don't really care
1066
       * since this message will never make it up here.
1067
       */
1068
1069
      /* So we accept it, if it is a Hello. If not, this will
1070
       * fail and trigger flight retransmissions after some time. */
1071
0
      ret =
1072
0
          recv_hello_request(session,
1073
0
                 bufel->msg.data,
1074
0
                 bufel->msg.size);
1075
0
      goto unexpected_packet;
1076
0
    default:
1077
1078
0
      _gnutls_record_log
1079
0
          ("REC[%p]: Received unexpected packet %d (%s) expecting %d (%s)\n",
1080
0
           session, recv->type,
1081
0
           _gnutls_packet2str(recv->type), type,
1082
0
           _gnutls_packet2str(type));
1083
1084
0
      gnutls_assert();
1085
0
      ret = GNUTLS_E_UNEXPECTED_PACKET;
1086
0
      goto unexpected_packet;
1087
0
    }
1088
0
  }
1089
1090
0
  return 0;
1091
1092
0
 unexpected_packet:
1093
1094
0
  if (IS_DTLS(session) && ret != GNUTLS_E_REHANDSHAKE) {
1095
0
    _mbuffer_xfree(&bufel);
1096
0
    RETURN_DTLS_EAGAIN_OR_TIMEOUT(session, ret);
1097
0
  }
1098
1099
0
 cleanup:
1100
0
  _mbuffer_xfree(&bufel);
1101
0
  return ret;
1102
1103
0
}
1104
1105
/* Checks the record headers and returns the length, version and
1106
 * content type.
1107
 */
1108
static void
1109
record_read_headers(gnutls_session_t session,
1110
        uint8_t headers[MAX_RECORD_HEADER_SIZE],
1111
        content_type_t type,
1112
        gnutls_handshake_description_t htype,
1113
        struct tls_record_st *record)
1114
0
{
1115
1116
  /* Read the first two bytes to determine if this is a
1117
   * version 2 message
1118
   */
1119
1120
0
#ifdef ENABLE_SSL2
1121
0
  if (htype == GNUTLS_HANDSHAKE_CLIENT_HELLO
1122
0
      && type == GNUTLS_HANDSHAKE && headers[0] > 127
1123
0
      && !(IS_DTLS(session))) {
1124
1125
    /* if msb set and expecting handshake message
1126
     * it should be SSL 2 hello
1127
     */
1128
0
    record->version[0] = 3; /* assume SSL 3.0 */
1129
0
    record->version[1] = 0;
1130
1131
0
    record->length = (((headers[0] & 0x7f) << 8)) | headers[1];
1132
1133
    /* SSL 2.0 headers */
1134
0
    record->header_size = record->packet_size = 2;
1135
0
    record->type = GNUTLS_HANDSHAKE;  /* we accept only v2 client hello
1136
               */
1137
1138
    /* in order to assist the handshake protocol.
1139
     * V2 compatibility is a mess.
1140
     */
1141
0
    record->v2 = 1;
1142
0
    record->epoch = 0;
1143
0
    memset(&record->sequence, 0, sizeof(record->sequence));
1144
1145
0
    _gnutls_record_log
1146
0
        ("REC[%p]: SSL 2.0 %s packet received. Length: %d\n",
1147
0
         session, _gnutls_packet2str(record->type), record->length);
1148
1149
0
  } else
1150
0
#endif
1151
0
  {
1152
    /* dtls version 1.0 and TLS version 1.x */
1153
0
#ifdef ENABLE_SSL2
1154
0
    record->v2 = 0;
1155
0
#endif
1156
1157
0
    record->type = headers[0];
1158
0
    record->version[0] = headers[1];
1159
0
    record->version[1] = headers[2];
1160
1161
0
    if (IS_DTLS(session)) {
1162
0
      record->sequence = _gnutls_read_uint64(&headers[3]);
1163
0
      record->length = _gnutls_read_uint16(&headers[11]);
1164
0
      record->epoch = record->sequence >> 48;
1165
0
    } else {
1166
0
      memset(&record->sequence, 0, sizeof(record->sequence));
1167
0
      record->length = _gnutls_read_uint16(&headers[3]);
1168
0
      record->epoch = session->security_parameters.epoch_read;
1169
0
    }
1170
1171
0
    _gnutls_record_log
1172
0
        ("REC[%p]: SSL %d.%d %s packet received. Epoch %d, length: %d\n",
1173
0
         session, (int)record->version[0],
1174
0
         (int)record->version[1],
1175
0
         _gnutls_packet2str(record->type), (int)record->epoch,
1176
0
         record->length);
1177
1178
0
  }
1179
1180
0
  record->packet_size += record->length;
1181
0
}
1182
1183
static int recv_headers(gnutls_session_t session,
1184
      record_parameters_st * record_params,
1185
      content_type_t type,
1186
      gnutls_handshake_description_t htype,
1187
      struct tls_record_st *record, unsigned int *ms)
1188
0
{
1189
0
  int ret;
1190
0
  gnutls_datum_t raw; /* raw headers */
1191
  /* Read the headers.
1192
   */
1193
0
  record->header_size = record->packet_size = RECORD_HEADER_SIZE(session);
1194
1195
0
  ret = _gnutls_io_read_buffered(session, record->header_size, -1, ms);
1196
0
  if (ret != record->header_size) {
1197
0
    if (ret < 0 && gnutls_error_is_fatal(ret) == 0)
1198
0
      return ret;
1199
1200
0
    if (ret > 0)
1201
0
      ret = GNUTLS_E_UNEXPECTED_PACKET_LENGTH;
1202
0
    else if (ret == 0)
1203
0
      ret = GNUTLS_E_PREMATURE_TERMINATION;
1204
1205
0
    return gnutls_assert_val(ret);
1206
0
  }
1207
1208
0
  ret = _mbuffer_linearize_align16(&session->internals.record_recv_buffer,
1209
0
           get_total_headers2(session,
1210
0
                  record_params));
1211
0
  if (ret < 0)
1212
0
    return gnutls_assert_val(ret);
1213
1214
0
  _mbuffer_head_get_first(&session->internals.record_recv_buffer, &raw);
1215
0
  if (raw.size < RECORD_HEADER_SIZE(session))
1216
0
    return gnutls_assert_val(GNUTLS_E_UNEXPECTED_PACKET_LENGTH);
1217
1218
0
  record_read_headers(session, raw.data, type, htype, record);
1219
1220
  /* Check if the DTLS epoch is valid */
1221
0
  if (IS_DTLS(session)) {
1222
0
    if (_gnutls_epoch_is_valid(session, record->epoch) == 0) {
1223
0
      _gnutls_audit_log(session,
1224
0
            "Discarded message[%lu] with invalid epoch %u.\n",
1225
0
            (unsigned long)record->sequence,
1226
0
            (unsigned int)(record->sequence >>
1227
0
               48));
1228
0
      gnutls_assert();
1229
      /* doesn't matter, just a fatal error */
1230
0
      return GNUTLS_E_UNEXPECTED_PACKET_LENGTH;
1231
0
    }
1232
0
  }
1233
1234
  /* Here we check if the Type of the received packet is
1235
   * ok.
1236
   */
1237
0
  if ((ret = check_recv_type(session, record->type)) < 0)
1238
0
    return gnutls_assert_val(ret);
1239
1240
  /* Here we check if the advertized version is the one we
1241
   * negotiated in the handshake.
1242
   */
1243
0
  if ((ret = record_check_version(session, htype, record->version)) < 0)
1244
0
    return gnutls_assert_val(ret);
1245
1246
0
  if (record->length == 0
1247
0
      || record->length > max_record_recv_size(session)) {
1248
0
    _gnutls_audit_log(session,
1249
0
          "Received packet with illegal length: %u (max: %u)\n",
1250
0
          (unsigned int)record->length,
1251
0
          (unsigned)max_record_recv_size(session));
1252
1253
0
    if (record->length == 0) {
1254
      /* Empty, unencrypted records are always unexpected. */
1255
0
      if (record_params->cipher->id == GNUTLS_CIPHER_NULL)
1256
0
        return
1257
0
            gnutls_assert_val
1258
0
            (GNUTLS_E_UNEXPECTED_PACKET);
1259
1260
0
      return gnutls_assert_val(GNUTLS_E_DECRYPTION_FAILED);
1261
0
    }
1262
0
    return gnutls_assert_val(GNUTLS_E_RECORD_OVERFLOW);
1263
0
  }
1264
1265
0
  _gnutls_record_log
1266
0
      ("REC[%p]: Expected Packet %s(%d)\n", session,
1267
0
       _gnutls_packet2str(type), type);
1268
0
  _gnutls_record_log
1269
0
      ("REC[%p]: Received Packet %s(%d) with length: %d\n", session,
1270
0
       _gnutls_packet2str(record->type), record->type, record->length);
1271
1272
0
  return 0;
1273
0
}
1274
1275
/* @ms: is the number of milliseconds to wait for data. Use zero for indefinite.
1276
 *
1277
 * This will receive record layer packets and add them to
1278
 * application_data_buffer and handshake_data_buffer.
1279
 *
1280
 * If the htype is not -1 then handshake timeouts
1281
 * will be enforced.
1282
 */
1283
ssize_t
1284
_gnutls_recv_in_buffers(gnutls_session_t session, content_type_t type,
1285
      gnutls_handshake_description_t htype, unsigned int ms)
1286
0
{
1287
0
  uint64_t packet_sequence;
1288
0
  gnutls_datum_t ciphertext;
1289
0
  mbuffer_st *bufel = NULL, *decrypted = NULL;
1290
0
  gnutls_datum_t t;
1291
0
  int ret;
1292
0
  unsigned int n_retries = 0;
1293
0
  record_parameters_st *record_params;
1294
0
  record_state_st *record_state;
1295
0
  struct tls_record_st record;
1296
0
  const version_entry_st *vers = get_version(session);
1297
1298
0
 begin:
1299
1300
0
  if (n_retries > DEFAULT_MAX_EMPTY_RECORDS) {
1301
0
    gnutls_assert();
1302
0
    return GNUTLS_E_TOO_MANY_EMPTY_PACKETS;
1303
0
  }
1304
1305
0
  if (session->internals.read_eof != 0) {
1306
    /* if we have already read an EOF
1307
     */
1308
0
    return 0;
1309
0
  } else if (session_is_valid(session) != 0
1310
0
       || session->internals.may_not_read != 0)
1311
0
    return gnutls_assert_val(GNUTLS_E_INVALID_SESSION);
1312
1313
  /* get the record state parameters */
1314
0
  ret = _gnutls_epoch_get(session, EPOCH_READ_CURRENT, &record_params);
1315
0
  if (ret < 0)
1316
0
    return gnutls_assert_val(ret);
1317
1318
  /* Safeguard against processing data with an incomplete cipher state. */
1319
0
  if (!record_params->initialized)
1320
0
    return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
1321
1322
0
  record_state = &record_params->read;
1323
1324
  /* receive headers */
1325
0
  ret =
1326
0
      recv_headers(session, record_params, type, htype, &record,
1327
0
       (!(session->
1328
0
          internals.flags & GNUTLS_NONBLOCK)) ? &ms : 0);
1329
0
  if (ret < 0) {
1330
0
    ret = gnutls_assert_val_fatal(ret);
1331
0
    goto recv_error;
1332
0
  }
1333
1334
0
  if (IS_DTLS(session))
1335
0
    packet_sequence = record.sequence;
1336
0
  else
1337
0
    packet_sequence = record_state->sequence_number;
1338
1339
  /* Read the packet data and insert it to record_recv_buffer.
1340
   */
1341
0
  ret =
1342
0
      _gnutls_io_read_buffered(session, record.packet_size,
1343
0
             record.type,
1344
0
             (!(session->
1345
0
          internals.flags & GNUTLS_NONBLOCK)) ?
1346
0
             &ms : 0);
1347
0
  if (ret != record.packet_size) {
1348
0
    gnutls_assert();
1349
0
    goto recv_error;
1350
0
  }
1351
1352
  /* ok now we are sure that we have read all the data - so
1353
   * move on !
1354
   */
1355
0
  ret = _mbuffer_linearize_align16(&session->internals.record_recv_buffer,
1356
0
           get_total_headers2(session,
1357
0
                  record_params));
1358
0
  if (ret < 0)
1359
0
    return gnutls_assert_val(ret);
1360
1361
0
  bufel =
1362
0
      _mbuffer_head_get_first(&session->internals.record_recv_buffer,
1363
0
            NULL);
1364
0
  if (bufel == NULL)
1365
0
    return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
1366
1367
  /* ignore CCS if TLS 1.3 is negotiated */
1368
0
  if (record.type == GNUTLS_CHANGE_CIPHER_SPEC && vers && vers->tls13_sem) {
1369
    /* if the CCS has arrived after Finished, abort the
1370
     * connection */
1371
0
    if (!session->internals.handshake_in_progress) {
1372
0
      return gnutls_assert_val(GNUTLS_E_UNEXPECTED_PACKET);
1373
0
    }
1374
0
    _gnutls_read_log("discarding change cipher spec in TLS1.3\n");
1375
    /* we use the same mechanism to retry as when
1376
     * receiving multiple empty TLS packets */
1377
0
    bufel =
1378
0
        _mbuffer_head_pop_first(&session->internals.
1379
0
              record_recv_buffer);
1380
0
    _mbuffer_xfree(&bufel);
1381
0
    n_retries++;
1382
0
    goto begin;
1383
0
  }
1384
1385
  /* We allocate the maximum possible to allow few compressed bytes to expand to a
1386
   * full record. Moreover we add space for any pad and the MAC (in case
1387
   * they are encrypted).
1388
   */
1389
0
  ret = max_decrypted_size(session) + MAX_PAD_SIZE + MAX_HASH_SIZE;
1390
0
  decrypted = _mbuffer_alloc_align16(ret, 0);
1391
0
  if (decrypted == NULL)
1392
0
    return gnutls_assert_val(GNUTLS_E_MEMORY_ERROR);
1393
1394
0
  _mbuffer_set_udata_size(decrypted, ret);
1395
0
  ciphertext.data =
1396
0
      (uint8_t *) _mbuffer_get_udata_ptr(bufel) + record.header_size;
1397
0
  ciphertext.size = record.length;
1398
1399
  /* decrypt the data we got.
1400
   */
1401
0
  t.data = _mbuffer_get_udata_ptr(decrypted);
1402
0
  t.size = _mbuffer_get_udata_size(decrypted);
1403
0
  ret =
1404
0
      _gnutls_decrypt(session, &ciphertext, &t,
1405
0
          &record.type, record_params, packet_sequence);
1406
0
  if (ret >= 0)
1407
0
    _mbuffer_set_udata_size(decrypted, ret);
1408
1409
0
  _mbuffer_head_remove_bytes(&session->internals.record_recv_buffer,
1410
0
           record.header_size + record.length);
1411
1412
0
  if (session->security_parameters.entity == GNUTLS_SERVER &&
1413
0
      session->internals.hsk_flags & HSK_EARLY_DATA_IN_FLIGHT) {
1414
0
    if (session->internals.hsk_flags & HSK_EARLY_DATA_ACCEPTED) {
1415
0
      if (ret < 0 ||
1416
          /* early data must always be encrypted, treat it
1417
           * as decryption failure if otherwise */
1418
0
          record_params->cipher->id == GNUTLS_CIPHER_NULL) {
1419
0
        _gnutls_record_log
1420
0
            ("REC[%p]: failed to decrypt early data, in epoch %d\n",
1421
0
             session, record_params->epoch);
1422
0
        ret = GNUTLS_E_DECRYPTION_FAILED;
1423
0
        goto sanity_check_error;
1424
0
      } else if (record.type == GNUTLS_APPLICATION_DATA) {
1425
0
        size_t decrypted_length =
1426
0
            _mbuffer_get_udata_size(decrypted);
1427
0
        _gnutls_record_log
1428
0
            ("REC[%p]: decrypted early data with length: %d, in epoch %d\n",
1429
0
             session,
1430
0
             (int)decrypted_length,
1431
0
             record_params->epoch);
1432
0
        if (decrypted_length >
1433
0
            session->
1434
0
            security_parameters.max_early_data_size -
1435
0
            session->internals.early_data_received) {
1436
0
          _gnutls_record_log
1437
0
              ("REC[%p]: max_early_data_size exceeded\n",
1438
0
               session);
1439
0
          ret = GNUTLS_E_UNEXPECTED_PACKET;
1440
0
          goto sanity_check_error;
1441
0
        }
1442
1443
0
        _mbuffer_enqueue(&session->
1444
0
             internals.early_data_recv_buffer,
1445
0
             decrypted);
1446
0
        session->internals.early_data_received +=
1447
0
            decrypted_length;
1448
1449
        /* Increase sequence number. We do both for TLS and DTLS, since in
1450
         * DTLS we also rely on that number (roughly) since it may get reported
1451
         * to application via gnutls_record_get_state().
1452
         */
1453
0
        if (sequence_increment
1454
0
            (session,
1455
0
             &record_state->sequence_number) != 0) {
1456
0
          session_invalidate(session);
1457
0
          gnutls_assert();
1458
0
          ret = GNUTLS_E_RECORD_LIMIT_REACHED;
1459
0
          goto sanity_check_error;
1460
0
        }
1461
1462
        /* decrypted is now accounted */
1463
0
        return GNUTLS_E_AGAIN;
1464
0
      }
1465
0
    } else {
1466
      /* We do not accept early data: skip decryption
1467
       * failure up to max_early_data_size. Otherwise,
1468
       * if the record is properly decrypted, treat it as
1469
       * the start of client's second flight.
1470
       */
1471
0
      if (record.type == GNUTLS_APPLICATION_DATA &&
1472
0
          (ret < 0 ||
1473
           /* early data must always be encrypted, treat it
1474
            * as decryption failure if otherwise */
1475
0
           record_params->cipher->id == GNUTLS_CIPHER_NULL)) {
1476
0
        if (record.length >
1477
0
            session->
1478
0
            security_parameters.max_early_data_size -
1479
0
            session->internals.early_data_received) {
1480
0
          _gnutls_record_log
1481
0
              ("REC[%p]: max_early_data_size exceeded\n",
1482
0
               session);
1483
0
          ret = GNUTLS_E_UNEXPECTED_PACKET;
1484
0
          goto sanity_check_error;
1485
0
        }
1486
1487
0
        _gnutls_record_log
1488
0
            ("REC[%p]: Discarded early data[%lu] due to invalid decryption, length: %u\n",
1489
0
             session, (unsigned long)packet_sequence,
1490
0
             (unsigned int)
1491
0
             record.length);
1492
0
        session->internals.early_data_received +=
1493
0
            record.length;
1494
        /* silently discard received data */
1495
0
        _mbuffer_xfree(&decrypted);
1496
0
        return gnutls_assert_val(GNUTLS_E_AGAIN);
1497
0
      } else {
1498
0
        session->internals.hsk_flags &=
1499
0
            ~HSK_EARLY_DATA_IN_FLIGHT;
1500
0
      }
1501
0
    }
1502
0
  }
1503
1504
0
  if (ret < 0) {
1505
0
    gnutls_assert();
1506
0
    _gnutls_audit_log(session,
1507
0
          "Discarded message[%lu] due to invalid decryption\n",
1508
0
          (unsigned long)packet_sequence);
1509
0
    goto sanity_check_error;
1510
0
  }
1511
1512
0
  if (IS_DTLS(session)) {
1513
    /* check for duplicates. We check after the message
1514
     * is processed and authenticated to avoid someone
1515
     * messing with our windows. */
1516
0
    if (likely
1517
0
        (!(session->
1518
0
           internals.flags & GNUTLS_NO_REPLAY_PROTECTION))) {
1519
0
      ret =
1520
0
          _dtls_record_check(record_params, packet_sequence);
1521
0
      if (ret < 0) {
1522
0
        _gnutls_record_log
1523
0
            ("REC[%p]: Discarded duplicate message[%u.%lu]: %s\n",
1524
0
             session,
1525
0
             (unsigned int)(record.sequence >> 48),
1526
0
             (unsigned long)(packet_sequence),
1527
0
             _gnutls_packet2str(record.type));
1528
0
        goto sanity_check_error;
1529
0
      }
1530
0
    }
1531
1532
0
    _gnutls_record_log
1533
0
        ("REC[%p]: Decrypted Packet[%u.%lu] %s(%d) with length: %d\n",
1534
0
         session,
1535
0
         (unsigned int)(record.sequence >> 48),
1536
0
         (unsigned long)packet_sequence,
1537
0
         _gnutls_packet2str(record.type), record.type,
1538
0
         (int)_mbuffer_get_udata_size(decrypted));
1539
1540
    /* store the last valid sequence number. We don't use that internally but
1541
     * callers of gnutls_record_get_state() could take advantage of it. */
1542
0
    record_state->sequence_number = record.sequence;
1543
0
  } else {
1544
0
    _gnutls_record_log
1545
0
        ("REC[%p]: Decrypted Packet[%lu] %s(%d) with length: %d\n",
1546
0
         session,
1547
0
         (unsigned long)packet_sequence,
1548
0
         _gnutls_packet2str(record.type), record.type,
1549
0
         (int)_mbuffer_get_udata_size(decrypted));
1550
1551
0
  }
1552
1553
  /* Increase sequence number. We do both for TLS and DTLS, since in
1554
   * DTLS we also rely on that number (roughly) since it may get reported
1555
   * to application via gnutls_record_get_state().
1556
   */
1557
0
  if (sequence_increment(session, &record_state->sequence_number) != 0) {
1558
0
    session_invalidate(session);
1559
0
    gnutls_assert();
1560
0
    ret = GNUTLS_E_RECORD_LIMIT_REACHED;
1561
0
    goto sanity_check_error;
1562
0
  }
1563
1564
  /* (originally for) TLS 1.0 CBC protection.
1565
   * Actually this code is called if we just received
1566
   * an empty packet. An empty TLS packet is usually
1567
   * sent to protect some vulnerabilities in the CBC mode.
1568
   * In that case we go to the beginning and start reading
1569
   * the next packet.
1570
   */
1571
0
  if (_mbuffer_get_udata_size(decrypted) == 0 &&
1572
      /* Under TLS 1.3, there are only AEAD ciphers and this
1573
       * logic is meaningless. Moreover, the implementation need
1574
       * to send correct alert upon receiving empty messages in
1575
       * certain occasions. Skip this and leave
1576
       * record_add_to_buffers() to handle the empty
1577
       * messages. */
1578
0
      !(vers && vers->tls13_sem)) {
1579
0
    _mbuffer_xfree(&decrypted);
1580
0
    n_retries++;
1581
0
    goto begin;
1582
0
  }
1583
1584
0
  if (_mbuffer_get_udata_size(decrypted) > max_decrypted_size(session)) {
1585
0
    _gnutls_audit_log
1586
0
        (session, "Received packet with illegal length: %u\n",
1587
0
         (unsigned int)ret);
1588
1589
0
    ret = gnutls_assert_val(GNUTLS_E_RECORD_OVERFLOW);
1590
0
    goto sanity_check_error;
1591
0
  }
1592
1593
0
#ifdef ENABLE_SSL2
1594
0
  if (record.v2) {
1595
0
    decrypted->htype = GNUTLS_HANDSHAKE_CLIENT_HELLO_V2;
1596
0
  } else
1597
0
#endif
1598
0
  {
1599
0
    uint8_t *p = _mbuffer_get_udata_ptr(decrypted);
1600
0
    decrypted->htype = p[0];
1601
0
  }
1602
1603
0
  ret =
1604
0
      record_add_to_buffers(session, &record, type, htype,
1605
0
          packet_sequence, decrypted);
1606
1607
  /* decrypted is now either deinitialized or buffered somewhere else */
1608
1609
0
  if (ret < 0)
1610
0
    return gnutls_assert_val(ret);
1611
1612
0
  return ret;
1613
1614
0
 discard:
1615
0
  session->internals.dtls.packets_dropped++;
1616
1617
  /* discard the whole received fragment. */
1618
0
  bufel = _mbuffer_head_pop_first(&session->internals.record_recv_buffer);
1619
0
  _mbuffer_xfree(&bufel);
1620
0
  return gnutls_assert_val(GNUTLS_E_AGAIN);
1621
1622
0
 sanity_check_error:
1623
0
  if (IS_DTLS(session)) {
1624
0
    session->internals.dtls.packets_dropped++;
1625
0
    ret = gnutls_assert_val(GNUTLS_E_AGAIN);
1626
0
    goto cleanup;
1627
0
  }
1628
1629
0
  session_unresumable(session);
1630
0
  session_invalidate(session);
1631
1632
0
 cleanup:
1633
0
  _mbuffer_xfree(&decrypted);
1634
0
  return ret;
1635
1636
0
 recv_error:
1637
0
  if (ret < 0
1638
0
      && (gnutls_error_is_fatal(ret) == 0 || ret == GNUTLS_E_TIMEDOUT))
1639
0
    return ret;
1640
1641
0
  if (type == GNUTLS_ALERT) { /* we were expecting close notify */
1642
0
    session_invalidate(session);
1643
0
    gnutls_assert();
1644
0
    return 0;
1645
0
  }
1646
1647
0
  if (IS_DTLS(session) && (ret == GNUTLS_E_DECRYPTION_FAILED ||
1648
0
         ret == GNUTLS_E_UNSUPPORTED_VERSION_PACKET ||
1649
0
         ret == GNUTLS_E_UNEXPECTED_PACKET_LENGTH ||
1650
0
         ret == GNUTLS_E_RECORD_OVERFLOW ||
1651
0
         ret == GNUTLS_E_UNEXPECTED_PACKET ||
1652
0
         ret == GNUTLS_E_ERROR_IN_FINISHED_PACKET ||
1653
0
         ret == GNUTLS_E_UNEXPECTED_HANDSHAKE_PACKET)) {
1654
0
    goto discard;
1655
0
  }
1656
1657
0
  session_invalidate(session);
1658
0
  session_unresumable(session);
1659
1660
0
  if (ret == 0)
1661
0
    return GNUTLS_E_UNEXPECTED_PACKET_LENGTH;
1662
0
  else
1663
0
    return ret;
1664
0
}
1665
1666
/* Returns a value greater than zero (>= 0) if buffers should be checked
1667
 * for data. */
1668
static ssize_t check_session_status(gnutls_session_t session, unsigned ms)
1669
0
{
1670
0
  int ret;
1671
1672
0
  if (session->internals.read_eof != 0) {
1673
    /* if we have already read an EOF
1674
     */
1675
0
    return 0;
1676
0
  } else if (session_is_valid(session) != 0
1677
0
       || session->internals.may_not_read != 0) {
1678
0
    gnutls_assert();
1679
0
    return GNUTLS_E_INVALID_SESSION;
1680
0
  }
1681
1682
0
  switch (session->internals.recv_state) {
1683
0
  case RECV_STATE_REAUTH:
1684
0
    session->internals.recv_state = RECV_STATE_0;
1685
1686
0
    ret = gnutls_reauth(session, 0);
1687
0
    if (ret < 0) {
1688
      /* a temp or fatal error, make sure we reset the state
1689
       * so we can resume on temp errors */
1690
0
      session->internals.recv_state = RECV_STATE_REAUTH;
1691
0
      return gnutls_assert_val(ret);
1692
0
    }
1693
1694
0
    return 1;
1695
0
  case RECV_STATE_REHANDSHAKE:
1696
0
    session->internals.recv_state = RECV_STATE_0;
1697
1698
0
    ret = gnutls_handshake(session);
1699
0
    if (ret < 0) {
1700
      /* a temp or fatal error, make sure we reset the state
1701
       * so we can resume on temp errors */
1702
0
      session->internals.recv_state = RECV_STATE_REHANDSHAKE;
1703
0
      return gnutls_assert_val(ret);
1704
0
    }
1705
1706
0
    return 1;
1707
0
  case RECV_STATE_ASYNC_HANDSHAKE:
1708
0
    ret =
1709
0
        _gnutls_recv_in_buffers(session, GNUTLS_HANDSHAKE, -1, ms);
1710
0
    if (ret < 0 && ret != GNUTLS_E_SESSION_EOF)
1711
0
      return gnutls_assert_val(ret);
1712
1713
0
    ret = _gnutls13_recv_async_handshake(session);
1714
0
    if (ret < 0)
1715
0
      return gnutls_assert_val(ret);
1716
1717
0
    return GNUTLS_E_AGAIN;
1718
0
  case RECV_STATE_EARLY_START_HANDLING:
1719
0
  case RECV_STATE_FALSE_START_HANDLING:
1720
0
    return 1;
1721
0
  case RECV_STATE_FALSE_START:
1722
    /* if false start is not complete we always expect for handshake packets
1723
     * prior to anything else. */
1724
0
    if (session->security_parameters.entity != GNUTLS_CLIENT ||
1725
0
        !(session->internals.flags & GNUTLS_ENABLE_FALSE_START))
1726
0
      return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
1727
1728
    /* Attempt to complete handshake - we only need to receive */
1729
0
    session->internals.recv_state = RECV_STATE_FALSE_START_HANDLING;
1730
0
    ret = gnutls_handshake(session);
1731
0
    if (ret < 0) {
1732
      /* a temp or fatal error, make sure we reset the state
1733
       * so we can resume on temp errors */
1734
0
      session->internals.recv_state = RECV_STATE_FALSE_START;
1735
0
      return gnutls_assert_val(ret);
1736
0
    }
1737
1738
0
    session->internals.recv_state = RECV_STATE_0;
1739
0
    return 1;
1740
0
  case RECV_STATE_EARLY_START:
1741
    /* if early start is not complete we always expect for handshake packets
1742
     * prior to anything else. */
1743
0
    if (session->security_parameters.entity != GNUTLS_SERVER ||
1744
0
        !(session->internals.flags & GNUTLS_ENABLE_EARLY_START))
1745
0
      return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
1746
1747
    /* Attempt to complete handshake - we only need to receive */
1748
0
    session->internals.recv_state = RECV_STATE_EARLY_START_HANDLING;
1749
0
    ret = gnutls_handshake(session);
1750
0
    if (ret < 0) {
1751
      /* a temp or fatal error, make sure we reset the state
1752
       * so we can resume on temp errors */
1753
0
      session->internals.recv_state = RECV_STATE_EARLY_START;
1754
0
      return gnutls_assert_val(ret);
1755
0
    }
1756
1757
0
    session->internals.recv_state = RECV_STATE_0;
1758
0
    return 1;
1759
0
  case RECV_STATE_DTLS_RETRANSMIT:
1760
0
    ret = _dtls_retransmit(session);
1761
0
    if (ret < 0)
1762
0
      return gnutls_assert_val(ret);
1763
1764
0
    session->internals.recv_state = RECV_STATE_0;
1765
1766
0
    FALLTHROUGH;
1767
0
  case RECV_STATE_0:
1768
1769
0
    _dtls_async_timer_check(session);
1770
0
    return 1;
1771
0
  default:
1772
0
    return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
1773
0
  }
1774
0
}
1775
1776
/* This function behaves exactly like read(). The only difference is
1777
 * that it accepts the gnutls_session_t and the content_type_t of data to
1778
 * receive (if called by the user the Content is Userdata only)
1779
 * It is intended to receive data, under the current session.
1780
 */
1781
ssize_t
1782
_gnutls_recv_int(gnutls_session_t session, content_type_t type,
1783
     uint8_t * data, size_t data_size, void *seq, unsigned int ms)
1784
0
{
1785
0
  int ret;
1786
1787
0
  if ((type != GNUTLS_ALERT && type != GNUTLS_HEARTBEAT)
1788
0
      && (data_size == 0 || data == NULL))
1789
0
    return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
1790
1791
0
  ret = check_session_status(session, ms);
1792
0
  if (ret <= 0)
1793
0
    return ret;
1794
1795
  /* If we have enough data in the cache do not bother receiving
1796
   * a new packet. (in order to flush the cache)
1797
   */
1798
0
  ret = get_data_from_buffers(session, type, data, data_size, seq);
1799
0
  if (ret != 0)
1800
0
    return ret;
1801
1802
0
  ret = _gnutls_recv_in_buffers(session, type, -1, ms);
1803
0
  if (ret < 0 && ret != GNUTLS_E_SESSION_EOF)
1804
0
    return gnutls_assert_val(ret);
1805
1806
0
  return get_data_from_buffers(session, type, data, data_size, seq);
1807
0
}
1808
1809
/**
1810
 * gnutls_packet_get:
1811
 * @packet: is a #gnutls_packet_t type.
1812
 * @data: will contain the data present in the @packet structure (may be %NULL)
1813
 * @sequence: the 8-bytes of the packet sequence number (may be %NULL)
1814
 *
1815
 * This function returns the data and sequence number associated with
1816
 * the received packet.
1817
 *
1818
 * Since: 3.3.5
1819
 **/
1820
1821
void gnutls_packet_get(gnutls_packet_t packet, gnutls_datum_t * data,
1822
           unsigned char *sequence)
1823
0
{
1824
0
  if (unlikely(packet == NULL)) {
1825
0
    gnutls_assert();
1826
0
    if (data) {
1827
0
      data->data = NULL;
1828
0
      data->size = 0;
1829
0
      return;
1830
0
    }
1831
0
  }
1832
1833
0
  assert(packet != NULL);
1834
1835
0
  if (sequence) {
1836
0
    _gnutls_write_uint64(packet->record_sequence, sequence);
1837
0
  }
1838
1839
0
  if (data) {
1840
0
    data->size = packet->msg.size - packet->mark;
1841
0
    data->data = packet->msg.data + packet->mark;
1842
0
  }
1843
0
}
1844
1845
/**
1846
 * gnutls_packet_deinit:
1847
 * @packet: is a pointer to a #gnutls_packet_st structure.
1848
 *
1849
 * This function will deinitialize all data associated with
1850
 * the received packet.
1851
 *
1852
 * Since: 3.3.5
1853
 **/
1854
void gnutls_packet_deinit(gnutls_packet_t packet)
1855
0
{
1856
0
  gnutls_free(packet);
1857
0
}
1858
1859
/**
1860
 * gnutls_record_discard_queued:
1861
 * @session: is a #gnutls_session_t type.
1862
 *
1863
 * This function discards all queued to be sent packets in a DTLS session.
1864
 * These are the packets queued after an interrupted gnutls_record_send().
1865
 *
1866
 * This function can only be used with transports where send() is
1867
 * an all-or-nothing operation (e.g., UDP). When partial writes are allowed
1868
 * this function will cause session errors.
1869
 *
1870
 * Returns: The number of bytes discarded.
1871
 *
1872
 * Since: 3.4.0
1873
 **/
1874
size_t gnutls_record_discard_queued(gnutls_session_t session)
1875
0
{
1876
0
  size_t ret = session->internals.record_send_buffer.byte_length;
1877
0
  _mbuffer_head_clear(&session->internals.record_send_buffer);
1878
0
  return ret;
1879
0
}
1880
1881
/**
1882
 * gnutls_record_recv_packet:
1883
 * @session: is a #gnutls_session_t type.
1884
 * @packet: the structure that will hold the packet data
1885
 *
1886
 * This is a lower-level function than gnutls_record_recv() and allows
1887
 * to directly receive the whole decrypted packet. That avoids a
1888
 * memory copy, and is intended to be used by applications seeking high
1889
 * performance.
1890
 *
1891
 * The received packet is accessed using gnutls_packet_get() and
1892
 * must be deinitialized using gnutls_packet_deinit(). The returned
1893
 * packet will be %NULL if the return value is zero (EOF).
1894
 *
1895
 * Returns: The number of bytes received and zero on EOF (for stream
1896
 * connections).  A negative error code is returned in case of an error.
1897
 *
1898
 * Since: 3.3.5
1899
 **/
1900
ssize_t
1901
gnutls_record_recv_packet(gnutls_session_t session, gnutls_packet_t * packet)
1902
0
{
1903
0
  int ret;
1904
1905
0
  if (packet == NULL)
1906
0
    return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
1907
1908
0
  ret =
1909
0
      check_session_status(session, session->internals.record_timeout_ms);
1910
0
  if (ret <= 0)
1911
0
    return ret;
1912
1913
0
  ret = get_packet_from_buffers(session, GNUTLS_APPLICATION_DATA, packet);
1914
0
  if (ret != 0)
1915
0
    return ret;
1916
1917
0
  ret = _gnutls_recv_in_buffers(session, GNUTLS_APPLICATION_DATA, -1,
1918
0
              session->internals.record_timeout_ms);
1919
0
  if (ret < 0 && ret != GNUTLS_E_SESSION_EOF)
1920
0
    return gnutls_assert_val(ret);
1921
1922
0
  return get_packet_from_buffers(session, GNUTLS_APPLICATION_DATA,
1923
0
               packet);
1924
0
}
1925
1926
static
1927
ssize_t append_data_to_corked(gnutls_session_t session, const void *data,
1928
            size_t data_size)
1929
0
{
1930
0
  int ret;
1931
1932
0
  if (IS_DTLS(session)) {
1933
0
    if (data_size +
1934
0
        session->internals.record_presend_buffer.length >
1935
0
        gnutls_dtls_get_data_mtu(session)) {
1936
0
      return gnutls_assert_val(GNUTLS_E_LARGE_PACKET);
1937
0
    }
1938
0
  }
1939
1940
0
  ret =
1941
0
      _gnutls_buffer_append_data(&session->internals.
1942
0
               record_presend_buffer, data, data_size);
1943
0
  if (ret < 0)
1944
0
    return gnutls_assert_val(ret);
1945
1946
0
  return data_size;
1947
0
}
1948
1949
/**
1950
 * gnutls_record_send:
1951
 * @session: is a #gnutls_session_t type.
1952
 * @data: contains the data to send
1953
 * @data_size: is the length of the data
1954
 *
1955
 * This function has the similar semantics with send().  The only
1956
 * difference is that it accepts a GnuTLS session, and uses different
1957
 * error codes.
1958
 * Note that if the send buffer is full, send() will block this
1959
 * function.  See the send() documentation for more information.
1960
 *
1961
 * You can replace the default push function which is send(), by using
1962
 * gnutls_transport_set_push_function().
1963
 *
1964
 * If the EINTR is returned by the internal push function
1965
 * then %GNUTLS_E_INTERRUPTED will be returned. If
1966
 * %GNUTLS_E_INTERRUPTED or %GNUTLS_E_AGAIN is returned, you must
1967
 * call this function again with the exact same parameters, or provide a
1968
 * %NULL pointer for @data and 0 for @data_size, in order to write the
1969
 * same data as before. If you wish to discard the previous data instead
1970
 * of retrying, you must call gnutls_record_discard_queued() before
1971
 * calling this function with different parameters. Note that the latter
1972
 * works only on special transports (e.g., UDP).
1973
 * cf. gnutls_record_get_direction().
1974
 *
1975
 * Note that in DTLS this function will return the %GNUTLS_E_LARGE_PACKET
1976
 * error code if the send data exceed the data MTU value - as returned
1977
 * by gnutls_dtls_get_data_mtu(). The errno value EMSGSIZE
1978
 * also maps to %GNUTLS_E_LARGE_PACKET.
1979
 * Note that since 3.2.13 this function can be called under cork in DTLS
1980
 * mode, and will refuse to send data over the MTU size by returning
1981
 * %GNUTLS_E_LARGE_PACKET.
1982
 *
1983
 * Returns: The number of bytes sent, or a negative error code.  The
1984
 *   number of bytes sent might be less than @data_size.  The maximum
1985
 *   number of bytes this function can send in a single call depends
1986
 *   on the negotiated maximum record size.
1987
 **/
1988
ssize_t
1989
gnutls_record_send(gnutls_session_t session, const void *data, size_t data_size)
1990
0
{
1991
0
  return gnutls_record_send2(session, data, data_size, 0, 0);
1992
0
}
1993
1994
/**
1995
 * gnutls_record_send2:
1996
 * @session: is a #gnutls_session_t type.
1997
 * @data: contains the data to send
1998
 * @data_size: is the length of the data
1999
 * @pad: padding to be added to the record
2000
 * @flags: must be zero
2001
 *
2002
 * This function is identical to gnutls_record_send() except that it
2003
 * takes an extra argument to specify padding to be added the record.
2004
 * To determine the maximum size of padding, use
2005
 * gnutls_record_get_max_size() and gnutls_record_overhead_size().
2006
 *
2007
 * Note that in order for GnuTLS to provide constant time processing
2008
 * of padding and data in TLS1.3, the flag %GNUTLS_SAFE_PADDING_CHECK
2009
 * must be used in gnutls_init().
2010
 *
2011
 * Returns: The number of bytes sent, or a negative error code.  The
2012
 *   number of bytes sent might be less than @data_size.  The maximum
2013
 *   number of bytes this function can send in a single call depends
2014
 *   on the negotiated maximum record size.
2015
 *
2016
 * Since: 3.6.3
2017
 **/
2018
ssize_t
2019
gnutls_record_send2(gnutls_session_t session, const void *data,
2020
        size_t data_size, size_t pad, unsigned flags)
2021
0
{
2022
0
  const version_entry_st *vers = get_version(session);
2023
0
  size_t max_pad = 0;
2024
0
  int ret;
2025
2026
0
  if (unlikely(!session->internals.initial_negotiation_completed)) {
2027
    /* this is to protect buggy applications from sending unencrypted
2028
     * data. We allow sending however, if we are in false or early start
2029
     * handshake state. */
2030
0
    gnutls_mutex_lock(&session->internals.post_negotiation_lock);
2031
2032
    /* we intentionally re-check the initial_negotation_completed variable
2033
     * to avoid locking during normal operation of gnutls_record_send2() */
2034
0
    if (!session->internals.initial_negotiation_completed &&
2035
0
        session->internals.recv_state != RECV_STATE_FALSE_START &&
2036
0
        session->internals.recv_state !=
2037
0
        RECV_STATE_FALSE_START_HANDLING
2038
0
        && session->internals.recv_state != RECV_STATE_EARLY_START
2039
0
        && session->internals.recv_state !=
2040
0
        RECV_STATE_EARLY_START_HANDLING
2041
0
        && !(session->
2042
0
       internals.hsk_flags & HSK_EARLY_DATA_IN_FLIGHT)) {
2043
2044
0
      gnutls_mutex_unlock(&session->
2045
0
              internals.post_negotiation_lock);
2046
0
      return
2047
0
          gnutls_assert_val
2048
0
          (GNUTLS_E_UNAVAILABLE_DURING_HANDSHAKE);
2049
0
    }
2050
0
    gnutls_mutex_unlock(&session->internals.post_negotiation_lock);
2051
0
  }
2052
2053
0
  if (unlikely(!vers))
2054
0
    return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
2055
2056
0
  if (vers->tls13_sem)
2057
0
    max_pad =
2058
0
        gnutls_record_get_max_size(session) -
2059
0
        gnutls_record_overhead_size(session);
2060
2061
0
  if (pad > max_pad)
2062
0
    return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
2063
2064
0
  switch (session->internals.rsend_state) {
2065
0
  case RECORD_SEND_NORMAL:
2066
0
    if (IS_KTLS_ENABLED(session, GNUTLS_KTLS_SEND)) {
2067
0
      return _gnutls_ktls_send(session, data, data_size);
2068
0
    } else {
2069
0
      return _gnutls_send_tlen_int(session,
2070
0
                 GNUTLS_APPLICATION_DATA,
2071
0
                 -1, EPOCH_WRITE_CURRENT,
2072
0
                 data, data_size, pad,
2073
0
                 MBUFFER_FLUSH);
2074
0
    }
2075
0
  case RECORD_SEND_CORKED:
2076
0
  case RECORD_SEND_CORKED_TO_KU:
2077
0
    return append_data_to_corked(session, data, data_size);
2078
0
  case RECORD_SEND_KEY_UPDATE_1:
2079
0
    _gnutls_buffer_reset(&session->
2080
0
             internals.record_key_update_buffer);
2081
2082
0
    ret =
2083
0
        _gnutls_buffer_append_data(&session->
2084
0
                 internals.record_key_update_buffer,
2085
0
                 data, data_size);
2086
0
    if (ret < 0)
2087
0
      return gnutls_assert_val(ret);
2088
2089
0
    session->internals.rsend_state = RECORD_SEND_KEY_UPDATE_2;
2090
0
    FALLTHROUGH;
2091
0
  case RECORD_SEND_KEY_UPDATE_2:
2092
0
    ret = gnutls_session_key_update(session, 0);
2093
0
    if (ret < 0)
2094
0
      return gnutls_assert_val(ret);
2095
2096
0
    session->internals.rsend_state = RECORD_SEND_KEY_UPDATE_3;
2097
0
    FALLTHROUGH;
2098
0
  case RECORD_SEND_KEY_UPDATE_3:
2099
0
    if (IS_KTLS_ENABLED(session, GNUTLS_KTLS_SEND)) {
2100
0
      return _gnutls_ktls_send(session,
2101
0
             session->
2102
0
             internals.record_key_update_buffer.
2103
0
             data,
2104
0
             session->
2105
0
             internals.record_key_update_buffer.length);
2106
0
    } else {
2107
0
      ret = _gnutls_send_int(session, GNUTLS_APPLICATION_DATA,
2108
0
                 -1, EPOCH_WRITE_CURRENT,
2109
0
                 session->
2110
0
                 internals.record_key_update_buffer.
2111
0
                 data,
2112
0
                 session->
2113
0
                 internals.record_key_update_buffer.
2114
0
                 length, MBUFFER_FLUSH);
2115
0
    }
2116
0
    _gnutls_buffer_clear(&session->
2117
0
             internals.record_key_update_buffer);
2118
0
    session->internals.rsend_state = RECORD_SEND_NORMAL;
2119
0
    if (ret < 0)
2120
0
      gnutls_assert();
2121
2122
0
    return ret;
2123
0
  default:
2124
0
    return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
2125
0
  }
2126
0
}
2127
2128
/**
2129
 * gnutls_record_send_early_data:
2130
 * @session: is a #gnutls_session_t type.
2131
 * @data: contains the data to send
2132
 * @data_size: is the length of the data
2133
 *
2134
 * This function can be used by a client to send data early in the
2135
 * handshake processes when resuming a session.  This is used to
2136
 * implement a zero-roundtrip (0-RTT) mode.  It has the same semantics
2137
 * as gnutls_record_send().
2138
 *
2139
 * There may be a limit to the amount of data sent as early data.  Use
2140
 * gnutls_record_get_max_early_data_size() to check the limit.  If the
2141
 * limit exceeds, this function returns
2142
 * %GNUTLS_E_RECORD_LIMIT_REACHED.
2143
 *
2144
 * Returns: The number of bytes sent, or a negative error code.  The
2145
 *   number of bytes sent might be less than @data_size.  The maximum
2146
 *   number of bytes this function can send in a single call depends
2147
 *   on the negotiated maximum record size.
2148
 *
2149
 * Since: 3.6.5
2150
 **/
2151
ssize_t gnutls_record_send_early_data(gnutls_session_t session,
2152
              const void *data, size_t data_size)
2153
0
{
2154
0
  int ret;
2155
2156
0
  if (session->security_parameters.entity != GNUTLS_CLIENT)
2157
0
    return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
2158
2159
0
  if (data_size == 0) {
2160
0
    return 0;
2161
0
  }
2162
2163
0
  if (xsum(session->internals.early_data_presend_buffer.length,
2164
0
     data_size) > session->security_parameters.max_early_data_size)
2165
0
    return gnutls_assert_val(GNUTLS_E_RECORD_LIMIT_REACHED);
2166
2167
0
  ret =
2168
0
      _gnutls_buffer_append_data(&session->internals.
2169
0
               early_data_presend_buffer, data,
2170
0
               data_size);
2171
0
  if (ret < 0)
2172
0
    return gnutls_assert_val(ret);
2173
2174
0
  session->internals.flags |= GNUTLS_ENABLE_EARLY_DATA;
2175
2176
0
  return ret;
2177
0
}
2178
2179
/**
2180
 * gnutls_record_send_file:
2181
 * @session: is a #gnutls_session_t type.
2182
 * @fd: file descriptor from which to read data.
2183
 * @offset: Is relative to file offset, denotes the starting location for
2184
 *          reading.  after function returns, it point to position following
2185
 *          last read byte.
2186
 * @count: is the length of the data in bytes to be read from file and send.
2187
 *
2188
 * This function sends data from @fd. If KTLS (kernel TLS) is enabled, it will
2189
 * use the sendfile() system call to avoid overhead of copying data between user
2190
 * space and the kernel. Otherwise, this functionality is merely emulated by
2191
 * calling read() and gnutls_record_send(). If this implementation is
2192
 * suboptimal, check whether KTLS is enabled using
2193
 * gnutls_transport_is_ktls_enabled().
2194
 *
2195
 * If @offset is NULL then file offset is incremented by number of bytes send,
2196
 * otherwise file offset remains unchanged.
2197
 *
2198
 * Returns: The number of bytes sent, or a negative error code.
2199
 **/
2200
ssize_t gnutls_record_send_file(gnutls_session_t session, int fd,
2201
        off_t * offset, size_t count)
2202
0
{
2203
0
  ssize_t ret;
2204
0
  size_t buf_len;
2205
0
  size_t sent = 0;
2206
0
  uint8_t *buf;
2207
0
  off_t saved_offset = 0;
2208
2209
0
  if (IS_KTLS_ENABLED(session, GNUTLS_KTLS_SEND)) {
2210
0
    return _gnutls_ktls_send_file(session, fd, offset, count);
2211
0
  }
2212
2213
0
  if (offset != NULL) {
2214
0
    saved_offset = lseek(fd, 0, SEEK_CUR);
2215
0
    if (saved_offset == (off_t) - 1) {
2216
0
      return GNUTLS_E_FILE_ERROR;
2217
0
    }
2218
0
    if (lseek(fd, *offset, SEEK_CUR) == -1) {
2219
0
      return GNUTLS_E_FILE_ERROR;
2220
0
    }
2221
0
  }
2222
2223
0
  buf_len = MIN(count, MAX(max_record_send_size(session), 512));
2224
2225
0
  buf = gnutls_malloc(buf_len);
2226
0
  if (buf == NULL) {
2227
0
    gnutls_assert();
2228
0
    ret = GNUTLS_E_MEMORY_ERROR;
2229
0
    goto end;
2230
0
  }
2231
2232
0
  while (sent < count) {
2233
0
    ret = read(fd, buf, MIN(buf_len, count - sent));
2234
0
    if (ret == 0) {
2235
0
      break;
2236
0
    } else if (ret == -1) {
2237
0
      if (errno == EAGAIN) {
2238
0
        ret = GNUTLS_E_AGAIN;
2239
0
        goto end;
2240
0
      }
2241
0
      ret = GNUTLS_E_FILE_ERROR;
2242
0
      goto end;
2243
0
    }
2244
2245
0
    ret = gnutls_record_send(session, buf, ret);
2246
0
    if (ret < 0) {
2247
0
      goto end;
2248
0
    }
2249
0
    if (INT_ADD_OVERFLOW(sent, ret)) {
2250
0
      gnutls_assert();
2251
0
      ret = GNUTLS_E_RECORD_OVERFLOW;
2252
0
      goto end;
2253
0
    }
2254
0
    sent += ret;
2255
0
  }
2256
2257
0
  ret = sent;
2258
2259
0
 end:
2260
0
  if (offset != NULL) {
2261
0
    if (likely(!INT_ADD_OVERFLOW(*offset, sent))) {
2262
0
      *offset += sent;
2263
0
    } else {
2264
0
      gnutls_assert();
2265
0
      ret = GNUTLS_E_RECORD_OVERFLOW;
2266
0
    }
2267
0
    lseek(fd, saved_offset, SEEK_SET);
2268
0
  }
2269
0
  gnutls_free(buf);
2270
0
  return ret;
2271
0
}
2272
2273
/**
2274
 * gnutls_record_recv_early_data:
2275
 * @session: is a #gnutls_session_t type.
2276
 * @data: the buffer that the data will be read into
2277
 * @data_size: the number of requested bytes
2278
 *
2279
 * This function can be used by a server to retrieve data sent early
2280
 * in the handshake processes when resuming a session.  This is used
2281
 * to implement a zero-roundtrip (0-RTT) mode.  It has the same
2282
 * semantics as gnutls_record_recv().
2283
 *
2284
 * This function can be called either in a handshake hook, or after
2285
 * the handshake is complete.
2286
 *
2287
 * Returns: The number of bytes received and zero when early data
2288
 * reading is complete.  A negative error code is returned in case of
2289
 * an error.  If no early data is received during the handshake, this
2290
 * function returns %GNUTLS_E_REQUESTED_DATA_NOT_AVAILABLE.  The
2291
 * number of bytes received might be less than the requested
2292
 * @data_size.
2293
 *
2294
 * Since: 3.6.5
2295
 **/
2296
ssize_t
2297
gnutls_record_recv_early_data(gnutls_session_t session, void *data,
2298
            size_t data_size)
2299
0
{
2300
0
  mbuffer_st *bufel;
2301
0
  gnutls_datum_t msg;
2302
0
  size_t length;
2303
2304
0
  if (session->security_parameters.entity != GNUTLS_SERVER)
2305
0
    return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
2306
2307
0
  bufel =
2308
0
      _mbuffer_head_get_first(&session->internals.early_data_recv_buffer,
2309
0
            &msg);
2310
0
  if (bufel == NULL)
2311
0
    return gnutls_assert_val(GNUTLS_E_REQUESTED_DATA_NOT_AVAILABLE);
2312
2313
0
  length = MIN(msg.size, data_size);
2314
0
  memcpy(data, msg.data, length);
2315
0
  _mbuffer_head_remove_bytes(&session->internals.early_data_recv_buffer,
2316
0
           length);
2317
2318
0
  return length;
2319
0
}
2320
2321
/**
2322
 * gnutls_record_cork:
2323
 * @session: is a #gnutls_session_t type.
2324
 *
2325
 * If called, gnutls_record_send() will no longer send any records.
2326
 * Any sent records will be cached until gnutls_record_uncork() is called.
2327
 *
2328
 * This function is safe to use with DTLS after GnuTLS 3.3.0.
2329
 *
2330
 * Since: 3.1.9
2331
 **/
2332
void gnutls_record_cork(gnutls_session_t session)
2333
0
{
2334
0
  session->internals.rsend_state = RECORD_SEND_CORKED;
2335
0
}
2336
2337
/**
2338
 * gnutls_record_uncork:
2339
 * @session: is a #gnutls_session_t type.
2340
 * @flags: Could be zero or %GNUTLS_RECORD_WAIT
2341
 *
2342
 * This resets the effect of gnutls_record_cork(), and flushes any pending
2343
 * data. If the %GNUTLS_RECORD_WAIT flag is specified then this
2344
 * function will block until the data is sent or a fatal error
2345
 * occurs (i.e., the function will retry on %GNUTLS_E_AGAIN and
2346
 * %GNUTLS_E_INTERRUPTED).
2347
 *
2348
 * If the flag %GNUTLS_RECORD_WAIT is not specified and the function
2349
 * is interrupted then the %GNUTLS_E_AGAIN or %GNUTLS_E_INTERRUPTED
2350
 * errors will be returned. To obtain the data left in the corked
2351
 * buffer use gnutls_record_check_corked().
2352
 *
2353
 * Returns: On success the number of transmitted data is returned, or
2354
 * otherwise a negative error code.
2355
 *
2356
 * Since: 3.1.9
2357
 **/
2358
int gnutls_record_uncork(gnutls_session_t session, unsigned int flags)
2359
0
{
2360
0
  int ret;
2361
0
  ssize_t total = 0;
2362
0
  record_send_state_t orig_state = session->internals.rsend_state;
2363
2364
0
  if (orig_state == RECORD_SEND_CORKED)
2365
0
    session->internals.rsend_state = RECORD_SEND_NORMAL;
2366
0
  else if (orig_state == RECORD_SEND_CORKED_TO_KU)
2367
0
    session->internals.rsend_state = RECORD_SEND_KEY_UPDATE_1;
2368
0
  else
2369
0
    return 0; /* nothing to be done */
2370
2371
0
  while (session->internals.record_presend_buffer.length > 0) {
2372
0
    if (flags == GNUTLS_RECORD_WAIT) {
2373
0
      do {
2374
0
        ret =
2375
0
            gnutls_record_send(session,
2376
0
                   session->internals.
2377
0
                   record_presend_buffer.
2378
0
                   data,
2379
0
                   session->internals.
2380
0
                   record_presend_buffer.
2381
0
                   length);
2382
0
      }
2383
0
      while (ret < 0
2384
0
             && (ret == GNUTLS_E_AGAIN
2385
0
           || ret == GNUTLS_E_INTERRUPTED));
2386
0
    } else {
2387
0
      ret =
2388
0
          gnutls_record_send(session,
2389
0
                 session->internals.
2390
0
                 record_presend_buffer.data,
2391
0
                 session->internals.
2392
0
                 record_presend_buffer.length);
2393
0
    }
2394
0
    if (ret < 0)
2395
0
      goto fail;
2396
2397
0
    session->internals.record_presend_buffer.data += ret;
2398
0
    session->internals.record_presend_buffer.length -= ret;
2399
0
    total += ret;
2400
0
  }
2401
2402
0
  return total;
2403
2404
0
 fail:
2405
0
  session->internals.rsend_state = orig_state;
2406
0
  return ret;
2407
0
}
2408
2409
/**
2410
 * gnutls_record_recv:
2411
 * @session: is a #gnutls_session_t type.
2412
 * @data: the buffer that the data will be read into
2413
 * @data_size: the number of requested bytes
2414
 *
2415
 * This function has the similar semantics with recv().  The only
2416
 * difference is that it accepts a GnuTLS session, and uses different
2417
 * error codes.
2418
 * In the special case that the peer requests a renegotiation, the
2419
 * caller will receive an error code of %GNUTLS_E_REHANDSHAKE.  In case
2420
 * of a client, this message may be simply ignored, replied with an alert
2421
 * %GNUTLS_A_NO_RENEGOTIATION, or replied with a new handshake,
2422
 * depending on the client's will. A server receiving this error code
2423
 * can only initiate a new handshake or terminate the session.
2424
 *
2425
 * If %EINTR is returned by the internal pull function (the default
2426
 * is recv()) then %GNUTLS_E_INTERRUPTED will be returned.  If
2427
 * %GNUTLS_E_INTERRUPTED or %GNUTLS_E_AGAIN is returned, you must
2428
 * call this function again to get the data.  See also
2429
 * gnutls_record_get_direction().
2430
 *
2431
 * Returns: The number of bytes received and zero on EOF (for stream
2432
 * connections).  A negative error code is returned in case of an error.
2433
 * The number of bytes received might be less than the requested @data_size.
2434
 **/
2435
ssize_t
2436
gnutls_record_recv(gnutls_session_t session, void *data, size_t data_size)
2437
0
{
2438
0
  if (unlikely(!session->internals.initial_negotiation_completed)) {
2439
    /* this is to protect buggy applications from sending unencrypted
2440
     * data. We allow sending however, if we are in false start handshake
2441
     * state. */
2442
0
    if (session->internals.recv_state != RECV_STATE_FALSE_START &&
2443
0
        session->internals.recv_state != RECV_STATE_EARLY_START)
2444
0
      return
2445
0
          gnutls_assert_val
2446
0
          (GNUTLS_E_UNAVAILABLE_DURING_HANDSHAKE);
2447
0
  }
2448
2449
0
  if (IS_KTLS_ENABLED(session, GNUTLS_KTLS_RECV)) {
2450
0
    return _gnutls_ktls_recv(session, data, data_size);
2451
0
  } else {
2452
0
    return _gnutls_recv_int(session, GNUTLS_APPLICATION_DATA,
2453
0
          data, data_size, NULL,
2454
0
          session->internals.record_timeout_ms);
2455
0
  }
2456
0
}
2457
2458
/**
2459
 * gnutls_record_recv_seq:
2460
 * @session: is a #gnutls_session_t type.
2461
 * @data: the buffer that the data will be read into
2462
 * @data_size: the number of requested bytes
2463
 * @seq: is the packet's 64-bit sequence number. Should have space for 8 bytes.
2464
 *
2465
 * This function is the same as gnutls_record_recv(), except that
2466
 * it returns in addition to data, the sequence number of the data.
2467
 * This is useful in DTLS where record packets might be received
2468
 * out-of-order. The returned 8-byte sequence number is an
2469
 * integer in big-endian format and should be
2470
 * treated as a unique message identification.
2471
 *
2472
 * Returns: The number of bytes received and zero on EOF.  A negative
2473
 *   error code is returned in case of an error.  The number of bytes
2474
 *   received might be less than @data_size.
2475
 *
2476
 * Since: 3.0
2477
 **/
2478
ssize_t
2479
gnutls_record_recv_seq(gnutls_session_t session, void *data,
2480
           size_t data_size, unsigned char *seq)
2481
0
{
2482
0
  return _gnutls_recv_int(session, GNUTLS_APPLICATION_DATA,
2483
0
        data, data_size, seq,
2484
0
        session->internals.record_timeout_ms);
2485
0
}
2486
2487
/**
2488
 * gnutls_record_set_timeout:
2489
 * @session: is a #gnutls_session_t type.
2490
 * @ms: is a timeout value in milliseconds
2491
 *
2492
 * This function sets the receive timeout for the record layer
2493
 * to the provided value. Use an @ms value of zero to disable
2494
 * timeout (the default), or %GNUTLS_INDEFINITE_TIMEOUT, to
2495
 * set an indefinite timeout.
2496
 *
2497
 * This function requires to set a pull timeout callback. See
2498
 * gnutls_transport_set_pull_timeout_function().
2499
 *
2500
 * Since: 3.1.7
2501
 **/
2502
void gnutls_record_set_timeout(gnutls_session_t session, unsigned int ms)
2503
0
{
2504
0
  session->internals.record_timeout_ms = ms;
2505
0
}
2506
2507
/**
2508
 * gnutls_handshake_write:
2509
 * @session: is a #gnutls_session_t type.
2510
 * @level: the current encryption level for reading a handshake message
2511
 * @data: the (const) handshake data to be processed
2512
 * @data_size: the size of data
2513
 *
2514
 * This function processes a handshake message in the encryption level
2515
 * specified with @level. Prior to calling this function, a handshake
2516
 * read callback must be set on @session. Use
2517
 * gnutls_handshake_set_read_function() to do this.
2518
 *
2519
 * Since: 3.7.0
2520
 */
2521
int
2522
gnutls_handshake_write(gnutls_session_t session,
2523
           gnutls_record_encryption_level_t level,
2524
           const void *data, size_t data_size)
2525
0
{
2526
0
  record_parameters_st *record_params;
2527
0
  record_state_st *record_state;
2528
0
  mbuffer_st *bufel;
2529
0
  uint8_t *p;
2530
0
  int ret;
2531
2532
  /* DTLS is not supported */
2533
0
  if (IS_DTLS(session))
2534
0
    return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
2535
2536
  /* Nothing to do */
2537
0
  if (data_size == 0)
2538
0
    return gnutls_assert_val(0);
2539
2540
  /* When using this, the outgoing handshake messages should
2541
   * also be handled manually unless KTLS is enabled exclusively
2542
   * in GNUTLS_KTLS_RECV mode in which case the outgoing messages
2543
   * are handled by GnuTLS.
2544
   */
2545
0
  if (!session->internals.h_read_func
2546
0
      && !IS_KTLS_ENABLED(session, GNUTLS_KTLS_RECV))
2547
0
    return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
2548
2549
0
  if (session->internals.initial_negotiation_completed) {
2550
0
    const version_entry_st *vers = get_version(session);
2551
0
    if (unlikely(vers == NULL || !vers->tls13_sem))
2552
0
      return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
2553
0
  }
2554
2555
0
  ret = _gnutls_epoch_get(session, EPOCH_READ_CURRENT, &record_params);
2556
0
  if (ret < 0)
2557
0
    return gnutls_assert_val(ret);
2558
2559
0
  record_state = &record_params->read;
2560
0
  if (record_state->level > level)
2561
0
    return gnutls_assert_val(GNUTLS_E_DECRYPTION_FAILED);
2562
2563
0
  bufel = _mbuffer_alloc_align16(data_size, 0);
2564
0
  if (bufel == NULL)
2565
0
    return gnutls_assert_val(GNUTLS_E_MEMORY_ERROR);
2566
2567
0
  memcpy(_mbuffer_get_udata_ptr(bufel), data, data_size);
2568
0
  _mbuffer_set_udata_size(bufel, data_size);
2569
0
  p = _mbuffer_get_udata_ptr(bufel);
2570
0
  bufel->htype = p[0];
2571
2572
0
  if (sequence_increment(session, &record_state->sequence_number) != 0) {
2573
0
    _mbuffer_xfree(&bufel);
2574
0
    return gnutls_assert_val(GNUTLS_E_RECORD_LIMIT_REACHED);
2575
0
  }
2576
2577
0
  _gnutls_record_buffer_put(session, GNUTLS_HANDSHAKE,
2578
0
          record_state->sequence_number, bufel);
2579
2580
0
  if (session->internals.initial_negotiation_completed)
2581
0
    return _gnutls13_recv_async_handshake(session);
2582
2583
0
  return 0;
2584
0
}