Coverage Report

Created: 2024-02-25 06:34

/src/kamailio/src/core/tcp_read.c
Line
Count
Source (jump to first uncovered line)
1
/*
2
 * Copyright (C) 2001-2003 FhG Fokus
3
 *
4
 * This file is part of Kamailio, a free SIP server.
5
 *
6
 * Kamailio is free software; you can redistribute it and/or modify
7
 * it under the terms of the GNU General Public License as published by
8
 * the Free Software Foundation; either version 2 of the License, or
9
 * (at your option) any later version
10
 *
11
 * Kamailio is distributed in the hope that it will be useful,
12
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14
 * GNU General Public License for more details.
15
 *
16
 * You should have received a copy of the GNU General Public License
17
 * along with this program; if not, write to the Free Software
18
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
19
 */
20
21
/** Kamailio core :: tcp readers processes, tcp read and pre-parse msg. functions.
22
 * @file tcp_read.c
23
 * @ingroup core
24
 * Module: @ref core
25
 */
26
27
#ifdef USE_TCP
28
29
#include <stdio.h>
30
#include <errno.h>
31
#include <string.h>
32
33
34
#include <sys/time.h>
35
#include <sys/types.h>
36
#include <sys/select.h>
37
#include <sys/socket.h>
38
39
#include <unistd.h>
40
#include <stdlib.h> /* for abort() */
41
42
#include "dprint.h"
43
#include "tcp_conn.h"
44
#include "tcp_read.h"
45
#include "tcp_stats.h"
46
#include "tcp_ev.h"
47
#include "pass_fd.h"
48
#include "globals.h"
49
#include "receive.h"
50
#include "timer.h"
51
#include "local_timer.h"
52
#include "ut.h"
53
#include "trim.h"
54
#include "pt.h"
55
#include "daemonize.h"
56
#include "cfg/cfg_struct.h"
57
#ifdef CORE_TLS
58
#include "tls/tls_server.h"
59
#else
60
#include "tls_hooks.h"
61
#endif /* CORE_TLS */
62
#ifdef USE_DST_BLOCKLIST
63
#include "dst_blocklist.h"
64
#endif /* USE_DST_BLOCKLIST */
65
66
#define HANDLE_IO_INLINE
67
#include "io_wait.h"
68
#include <fcntl.h> /* must be included after io_wait.h if SIGIO_RT is used */
69
#include "tsend.h"
70
#include "forward.h"
71
#include "events.h"
72
#include "stun.h"
73
#include "nonsip_hooks.h"
74
75
#ifdef READ_HTTP11
76
0
#define HTTP11CONTINUE "HTTP/1.1 100 Continue\r\nContent-Length: 0\r\n\r\n"
77
0
#define HTTP11CONTINUE_LEN (sizeof(HTTP11CONTINUE) - 1)
78
#endif
79
80
#define TCPCONN_TIMEOUT_MIN_RUN 1 /* run the timers each new tick */
81
82
/* types used in io_wait* */
83
enum fd_types
84
{
85
  F_NONE,
86
  F_TCPMAIN,
87
  F_TCPCONN
88
};
89
90
/* list of tcp connections handled by this process */
91
static struct tcp_connection *tcp_conn_lst = 0;
92
static io_wait_h io_w; /* io_wait handler*/
93
static int tcpmain_sock = -1;
94
95
static struct local_timer tcp_reader_ltimer;
96
static ticks_t tcp_reader_prev_ticks;
97
98
int is_msg_complete(struct tcp_req *r);
99
100
int ksr_tcp_accept_hep3 = 0;
101
int ksr_tcp_accept_haproxy = 0;
102
103
0
#define TCP_SCRIPT_MODE_CONTINUE (1 << 0)
104
int ksr_tcp_script_mode = 0;
105
106
/**
107
 * control cloning of TCP receive buffer
108
 * - needed for operations working directly inside the buffer
109
 *   (like msg_apply_changes())
110
 */
111
#define TCP_CLONE_RCVBUF
112
static int tcp_clone_rcvbuf = 0;
113
114
int tcp_set_clone_rcvbuf(int v)
115
0
{
116
0
  int r;
117
0
  r = tcp_clone_rcvbuf;
118
0
  tcp_clone_rcvbuf = v;
119
0
  return r;
120
0
}
121
122
int tcp_get_clone_rcvbuf(void)
123
0
{
124
0
  return tcp_clone_rcvbuf;
125
0
}
126
127
#ifdef READ_HTTP11
128
int tcp_http11_continue(struct tcp_connection *c)
129
0
{
130
0
  struct dest_info dst;
131
0
  char *p;
132
0
  struct msg_start fline;
133
0
  int ret;
134
0
  str msg;
135
136
0
  ret = 0;
137
138
0
  msg.s = c->req.start;
139
0
  msg.len = c->req.pos - c->req.start;
140
0
#ifdef READ_MSRP
141
  /* skip if MSRP message */
142
0
  if(c->req.flags & F_TCP_REQ_MSRP_FRAME)
143
0
    return 0;
144
0
#endif
145
0
  p = parse_first_line(msg.s, msg.len, &fline);
146
0
  if(p == NULL)
147
0
    return 0;
148
149
0
  if(fline.type != SIP_REQUEST)
150
0
    return 0;
151
152
  /* check if http request */
153
0
  if(fline.u.request.version.len < HTTP_VERSION_LEN
154
0
      || strncasecmp(
155
0
          fline.u.request.version.s, HTTP_VERSION, HTTP_VERSION_LEN))
156
0
    return 0;
157
158
  /* check for Expect header */
159
0
  if(str_casesearch_strz(&msg, "Expect: 100-continue") != NULL) {
160
0
    init_dst_from_rcv(&dst, &c->rcv);
161
0
    if(tcp_send(&dst, 0, HTTP11CONTINUE, HTTP11CONTINUE_LEN) < 0) {
162
0
      LM_ERR("HTTP/1.1 continue failed\n");
163
0
    }
164
0
  }
165
  /* check for Transfer-Encoding header */
166
0
  if(str_casesearch_strz(&msg, "Transfer-Encoding: chunked") != NULL) {
167
0
    c->req.flags |= F_TCP_REQ_BCHUNKED;
168
0
    ret = 1;
169
0
  }
170
  /* check for HTTP Via header
171
   * - HTTP Via format is different that SIP Via
172
   * - workaround: replace with Hia to be ignored by SIP parser
173
   */
174
0
  if((p = str_casesearch_strz(&msg, "\nVia:")) != NULL) {
175
0
    p++;
176
0
    *p = 'H';
177
0
    LM_DBG("replaced HTTP Via with Hia [[\n%.*s]]\n", msg.len, msg.s);
178
0
  }
179
0
  return ret;
180
0
}
181
#endif /* HTTP11 */
182
183
184
/** reads data from an existing tcp connection.
185
 * Side-effects: blocklisting, sets connection state to S_CONN_OK, tcp stats.
186
 * @param fd - connection file descriptor
187
 * @param c - tcp connection structure. c->state might be changed and
188
 *             receive info might be used for blocklisting.
189
 * @param buf - buffer where the received data will be stored.
190
 * @param b_size - buffer size.
191
 * @param flags - value/result - used to signal a seen or "forced" EOF on the
192
 *     connection (when it is known that no more data will come after the
193
 *     current socket buffer is emptied )=> return/signal EOF on the first
194
 *     short read (=> don't use it on POLLPRI, as OOB data will cause short
195
 *     reads even if there are still remaining bytes in the socket buffer)
196
 *     input: RD_CONN_FORCE_EOF  - force EOF after the first successful read
197
 *                                 (bytes_read >=0 )
198
 *     output: RD_CONN_SHORT_READ - if the read exhausted all the bytes
199
 *                                  in the socket read buffer.
200
 *             RD_CONN_EOF - if EOF detected (0 bytes read) or forced via
201
 *                           RD_CONN_FORCE_EOF.
202
 *             RD_CONN_REPEAT_READ - the read should be repeated immediately
203
 *                                   (used only by the tls code for now).
204
 *     Note: RD_CONN_SHORT_READ & RD_CONN_EOF _are_ not cleared internally,
205
 *           so one should clear them before calling this function.
206
 * @return number of bytes read, 0 on EOF or -1 on error,
207
 * on EOF it also sets c->state to S_CONN_EOF.
208
 * (to distinguish from reads that would block which could return 0)
209
 * RD_CONN_SHORT_READ is also set in *flags for short reads.
210
 * EOF checking should be done by checking the RD_CONN_EOF flag.
211
 */
212
int tcp_read_data(int fd, struct tcp_connection *c, char *buf, int b_size,
213
    rd_conn_flags_t *flags)
214
0
{
215
0
  int bytes_read;
216
217
0
again:
218
0
  bytes_read = read(fd, buf, b_size);
219
220
0
  if(likely(bytes_read != b_size)) {
221
0
    if(unlikely(bytes_read == -1)) {
222
0
      if(errno == EWOULDBLOCK || errno == EAGAIN) {
223
0
        bytes_read = 0; /* nothing has been read */
224
0
      } else if(errno == EINTR) {
225
0
        goto again;
226
0
      } else {
227
0
        if(unlikely(c->state == S_CONN_CONNECT)) {
228
0
          switch(errno) {
229
0
            case ECONNRESET:
230
0
#ifdef USE_DST_BLOCKLIST
231
0
              dst_blocklist_su(BLST_ERR_CONNECT, c->rcv.proto,
232
0
                  &c->rcv.src_su, &c->send_flags, 0);
233
0
#endif /* USE_DST_BLOCKLIST */
234
0
              TCP_EV_CONNECT_RST(errno, TCP_LADDR(c),
235
0
                  TCP_LPORT(c), TCP_PSU(c), TCP_PROTO(c));
236
0
              break;
237
0
            case ETIMEDOUT:
238
0
#ifdef USE_DST_BLOCKLIST
239
0
              dst_blocklist_su(BLST_ERR_CONNECT, c->rcv.proto,
240
0
                  &c->rcv.src_su, &c->send_flags, 0);
241
0
#endif /* USE_DST_BLOCKLIST */
242
0
              TCP_EV_CONNECT_TIMEOUT(errno, TCP_LADDR(c),
243
0
                  TCP_LPORT(c), TCP_PSU(c), TCP_PROTO(c));
244
0
              break;
245
0
            default:
246
0
              TCP_EV_CONNECT_ERR(errno, TCP_LADDR(c),
247
0
                  TCP_LPORT(c), TCP_PSU(c), TCP_PROTO(c));
248
0
          }
249
0
          TCP_STATS_CONNECT_FAILED();
250
0
        } else {
251
0
          switch(errno) {
252
0
            case ECONNRESET:
253
0
              TCP_STATS_CON_RESET();
254
0
#ifdef USE_DST_BLOCKLIST
255
0
              dst_blocklist_su(BLST_ERR_SEND, c->rcv.proto,
256
0
                  &c->rcv.src_su, &c->send_flags, 0);
257
0
#endif /* USE_DST_BLOCKLIST */
258
0
              break;
259
0
            case ETIMEDOUT:
260
0
#ifdef USE_DST_BLOCKLIST
261
0
              dst_blocklist_su(BLST_ERR_SEND, c->rcv.proto,
262
0
                  &c->rcv.src_su, &c->send_flags, 0);
263
0
#endif /* USE_DST_BLOCKLIST */
264
0
              break;
265
0
          }
266
0
        }
267
0
        LOG(cfg_get(core, core_cfg, corelog),
268
0
            "error reading: %s (%d) ([%s]:%u ->", strerror(errno),
269
0
            errno, ip_addr2a(&c->rcv.src_ip), c->rcv.src_port);
270
0
        LOG(cfg_get(core, core_cfg, corelog), "-> [%s]:%u)\n",
271
0
            ip_addr2a(&c->rcv.dst_ip), c->rcv.dst_port);
272
0
        if(errno == ETIMEDOUT) {
273
0
          c->event = TCP_CLOSED_TIMEOUT;
274
0
        } else if(errno == ECONNRESET) {
275
0
          c->event = TCP_CLOSED_RESET;
276
0
        }
277
0
        return -1;
278
0
      }
279
0
    } else if(unlikely((bytes_read == 0) || (*flags & RD_CONN_FORCE_EOF))) {
280
0
      LM_DBG("EOF on connection %p (state: %u, flags: %x) - FD %d,"
281
0
           " bytes %d, rd-flags %x ([%s]:%u -> [%s]:%u)",
282
0
          c, c->state, c->flags, fd, bytes_read, *flags,
283
0
          ip_addr2a(&c->rcv.src_ip), c->rcv.src_port,
284
0
          ip_addr2a(&c->rcv.dst_ip), c->rcv.dst_port);
285
0
      c->state = S_CONN_EOF;
286
0
      *flags |= RD_CONN_EOF;
287
0
      c->event = TCP_CLOSED_EOF;
288
0
    } else {
289
0
      if(unlikely(c->state == S_CONN_CONNECT
290
0
            || c->state == S_CONN_ACCEPT)) {
291
0
        TCP_STATS_ESTABLISHED(c->state);
292
0
        c->state = S_CONN_OK;
293
0
      }
294
0
    }
295
    /* short read */
296
0
    *flags |= RD_CONN_SHORT_READ;
297
0
  } else { /* else normal full read */
298
0
    if(unlikely(c->state == S_CONN_CONNECT || c->state == S_CONN_ACCEPT)) {
299
0
      TCP_STATS_ESTABLISHED(c->state);
300
0
      c->state = S_CONN_OK;
301
0
    }
302
0
  }
303
0
  return bytes_read;
304
0
}
305
306
307
/* reads next available bytes
308
 *   c- tcp connection used for reading, tcp_read changes also c->state on
309
 *      EOF and c->req.error on read error
310
 *   * flags - value/result - used to signal a seen or "forced" EOF on the
311
 *     connection (when it is known that no more data will come after the
312
 *     current socket buffer is emptied )=> return/signal EOF on the first
313
 *     short read (=> don't use it on POLLPRI, as OOB data will cause short
314
 *      reads even if there are still remaining bytes in the socket buffer)
315
 * return number of bytes read, 0 on EOF or -1 on error,
316
 * on EOF it also sets c->state to S_CONN_EOF.
317
 * (to distinguish from reads that would block which could return 0)
318
 * RD_CONN_SHORT_READ is also set in *flags for short reads.
319
 * sets also r->error */
320
int tcp_read(struct tcp_connection *c, rd_conn_flags_t *flags)
321
0
{
322
0
  int bytes_free, bytes_read;
323
0
  struct tcp_req *r;
324
0
  int fd;
325
326
0
  r = &c->req;
327
0
  fd = c->fd;
328
0
  bytes_free = r->b_size - (unsigned int)(r->pos - r->buf);
329
330
0
  if(unlikely(bytes_free <= 0)) {
331
0
    LM_ERR("buffer overrun, dropping ([%s]:%u -> [%s]:%u)\n",
332
0
        ip_addr2a(&c->rcv.src_ip), c->rcv.src_port,
333
0
        ip_addr2a(&c->rcv.dst_ip), c->rcv.dst_port);
334
0
    r->error = TCP_REQ_OVERRUN;
335
0
    return -1;
336
0
  }
337
0
  bytes_read = tcp_read_data(fd, c, r->pos, bytes_free, flags);
338
0
  if(unlikely(bytes_read < 0)) {
339
0
    r->error = TCP_READ_ERROR;
340
0
    return -1;
341
0
  }
342
#ifdef EXTRA_DEBUG
343
  LM_DBG("read %d bytes:\n%.*s\n", bytes_read, bytes_read, r->pos);
344
#endif
345
0
  r->pos += bytes_read;
346
0
  return bytes_read;
347
0
}
348
349
350
/* reads all headers (until double crlf), & parses the content-length header
351
 * (WARNING: inefficient, tries to reuse receive_msg but will go through
352
 * the headers twice [once here looking for Content-Length and for the end
353
 * of the headers and once in receive_msg]; a more speed efficient version will
354
 * result in either major code duplication or major changes to the receive code)
355
 * returns number of bytes read & sets r->state & r->body
356
 * when either r->body!=0 or r->state==H_BODY =>
357
 * all headers have been read. It should be called in a while loop.
358
 * returns < 0 if error or 0 if EOF */
359
int tcp_read_headers(struct tcp_connection *c, rd_conn_flags_t *read_flags)
360
0
{
361
0
  int bytes, remaining;
362
0
  char *p;
363
0
  struct tcp_req *r;
364
0
  unsigned int mc; /* magic cookie */
365
0
  unsigned short body_len;
366
0
  struct timeval tvnow;
367
0
  long long tvdiff;
368
369
0
#ifdef READ_MSRP
370
0
  char *mfline;
371
0
  str mtransid;
372
0
#endif
373
374
0
#define crlf_default_skip_case \
375
0
  case '\n':                 \
376
0
    r->state = H_LF;       \
377
0
    break;                 \
378
0
  default:                   \
379
0
    r->state = H_SKIP
380
381
0
#define content_len_beg_case                         \
382
0
  case ' ':                                        \
383
0
  case '\t':                                       \
384
0
    if(!TCP_REQ_HAS_CLEN(r))                     \
385
0
      r->state = H_STARTWS;                    \
386
0
    else                                         \
387
0
      r->state = H_SKIP;                       \
388
    /* not interested if we already found one */ \
389
0
    break;                                       \
390
0
  case 'C':                                        \
391
0
  case 'c':                                        \
392
0
    if(!TCP_REQ_HAS_CLEN(r))                     \
393
0
      r->state = H_CONT_LEN1;                  \
394
0
    else                                         \
395
0
      r->state = H_SKIP;                       \
396
0
    break;                                       \
397
0
  case 'l':                                        \
398
0
  case 'L':                                        \
399
    /* short form for Content-Length */          \
400
0
    if(!TCP_REQ_HAS_CLEN(r))                     \
401
0
      r->state = H_L_COLON;                    \
402
0
    else                                         \
403
0
      r->state = H_SKIP;                       \
404
0
    break
405
406
0
#define change_state(upper, lower, newstate) \
407
0
  switch(*p) {                             \
408
0
    case upper:                          \
409
0
    case lower:                          \
410
0
      r->state = (newstate);           \
411
0
      break;                           \
412
0
      crlf_default_skip_case;          \
413
0
  }
414
415
0
#define change_state_case(state0, upper, lower, newstate) \
416
0
  case state0:                                          \
417
0
    change_state(upper, lower, newstate);             \
418
0
    p++;                                              \
419
0
    break
420
421
422
0
  r = &c->req;
423
0
  if(r->parsed < r->buf || r->parsed > r->buf + r->b_size) {
424
0
    if(r->parsed < r->buf && (unsigned char)r->state == H_SKIP_EMPTY) {
425
      /* give it a chance to parse from beginning */
426
0
      LM_WARN("resetting parsed pointer (buf:%p parsed:%p bsize:%u)\n",
427
0
          r->buf, r->parsed, r->b_size);
428
0
      r->parsed = r->buf;
429
0
    } else {
430
0
      LM_ERR("out of bounds parsed pointer (buf:%p parsed:%p bsize:%u)\n",
431
0
          r->buf, r->parsed, r->b_size);
432
0
      r->parsed = r->buf;
433
0
      r->content_len = 0;
434
0
      r->error = TCP_REQ_BAD_LEN;
435
0
      r->state = H_SKIP; /* skip state now */
436
0
      return -1;
437
0
    }
438
0
  }
439
  /* if we still have some unparsed part, parse it first, don't do the read*/
440
0
  if(unlikely(r->parsed < r->pos)) {
441
0
    bytes = 0;
442
0
  } else {
443
0
#ifdef USE_TLS
444
0
    if(unlikely(c->type == PROTO_TLS))
445
0
      bytes = tls_read(c, read_flags);
446
0
    else
447
0
#endif
448
0
      bytes = tcp_read(c, read_flags);
449
0
    if(bytes <= 0)
450
0
      return bytes;
451
0
    gettimeofday(&tvnow, NULL);
452
0
    tvdiff = 1000000 * (tvnow.tv_sec - r->tvrstart.tv_sec)
453
0
         + (tvnow.tv_usec - r->tvrstart.tv_usec);
454
0
    if(tvdiff >= ksr_tcp_msg_read_timeout * 1000000) {
455
0
      LM_ERR("message reading timeout after %lld usec\n", tvdiff);
456
0
      r->parsed = r->buf;
457
0
      r->content_len = 0;
458
0
      r->error = TCP_REQ_BAD_LEN;
459
0
      r->state = H_SKIP; /* skip now */
460
0
      return -1;
461
0
    }
462
0
  }
463
0
  p = r->parsed;
464
465
0
  while(p < r->pos && r->error == TCP_REQ_OK) {
466
0
    switch((unsigned char)r->state) {
467
0
      case H_BODY: /* read the body*/
468
0
        remaining = r->pos - p;
469
0
        if(remaining > r->bytes_to_go)
470
0
          remaining = r->bytes_to_go;
471
0
        r->bytes_to_go -= remaining;
472
0
        p += remaining;
473
0
        if(r->bytes_to_go == 0) {
474
0
          r->flags |= F_TCP_REQ_COMPLETE;
475
0
          goto skip;
476
0
        }
477
0
        break;
478
479
0
      case H_SKIP:
480
        /* find lf, we are in this state if we are not interested
481
         * in anything till end of line*/
482
0
        p = q_memchr(p, '\n', r->pos - p);
483
0
        if(p) {
484
0
#ifdef READ_MSRP
485
          /* catch if it is MSRP or not with first '\n' */
486
0
          if(!((r->flags & F_TCP_REQ_MSRP_NO)
487
0
                 || (r->flags & F_TCP_REQ_MSRP_FRAME))) {
488
0
            if((r->pos - r->start) > 5
489
0
                && strncmp(r->start, "MSRP ", 5) == 0) {
490
0
              r->flags |= F_TCP_REQ_MSRP_FRAME;
491
0
            } else {
492
0
              r->flags |= F_TCP_REQ_MSRP_NO;
493
0
            }
494
0
          }
495
0
#endif
496
0
          p++;
497
0
          r->state = H_LF;
498
0
        } else {
499
0
          p = r->pos;
500
0
        }
501
0
        break;
502
503
0
      case H_LF:
504
        /* terminate on LF CR LF or LF LF */
505
0
        switch(*p) {
506
0
          case '\r':
507
0
            r->state = H_LFCR;
508
0
            break;
509
0
          case '\n':
510
            /* found LF LF */
511
0
            r->state = H_BODY;
512
0
#ifdef READ_HTTP11
513
0
            if(cfg_get(tcp, tcp_cfg, accept_no_cl) != 0)
514
0
              tcp_http11_continue(c);
515
0
#endif
516
0
            if(TCP_REQ_HAS_CLEN(r)) {
517
0
              r->body = p + 1;
518
0
              r->bytes_to_go = r->content_len;
519
0
              if(r->bytes_to_go == 0) {
520
0
                r->flags |= F_TCP_REQ_COMPLETE;
521
0
                p++;
522
0
                goto skip;
523
0
              }
524
0
            } else {
525
0
              if(cfg_get(tcp, tcp_cfg, accept_no_cl) != 0) {
526
0
#ifdef READ_MSRP
527
                /* if MSRP message */
528
0
                if(c->req.flags & F_TCP_REQ_MSRP_FRAME) {
529
0
                  r->body = p + 1;
530
                  /* at least 3 bytes: 0\r\n */
531
0
                  r->bytes_to_go = 3;
532
0
                  p++;
533
0
                  r->content_len = 0;
534
0
                  r->state = H_MSRP_BODY;
535
0
                  break;
536
0
                }
537
0
#endif
538
539
0
#ifdef READ_HTTP11
540
0
                if(TCP_REQ_BCHUNKED(r)) {
541
0
                  r->body = p + 1;
542
                  /* at least 3 bytes: 0\r\n */
543
0
                  r->bytes_to_go = 3;
544
0
                  p++;
545
0
                  r->content_len = 0;
546
0
                  r->state = H_HTTP11_CHUNK_START;
547
0
                  break;
548
0
                }
549
0
#endif
550
0
                r->body = p + 1;
551
0
                r->bytes_to_go = 0;
552
0
                r->flags |= F_TCP_REQ_COMPLETE;
553
0
                p++;
554
0
                goto skip;
555
0
              } else {
556
0
                LM_DBG("no clen, p=%X\n", *p);
557
0
                r->error = TCP_REQ_BAD_LEN;
558
0
              }
559
0
            }
560
0
            break;
561
0
          case '-':
562
0
            r->state = H_SKIP;
563
0
#ifdef READ_MSRP
564
            /* catch end of MSRP frame without body
565
             *     '-------sessid$\r\n'
566
             * follows headers without extra CRLF */
567
0
            if(r->flags & F_TCP_REQ_MSRP_FRAME) {
568
0
              p--;
569
0
              r->state = H_MSRP_BODY_END;
570
0
            }
571
0
#endif
572
0
            break;
573
0
            content_len_beg_case;
574
0
          default:
575
0
            r->state = H_SKIP;
576
0
        }
577
0
        p++;
578
0
        break;
579
0
      case H_LFCR:
580
0
        if(*p == '\n') {
581
          /* found LF CR LF */
582
0
          r->state = H_BODY;
583
0
#ifdef READ_HTTP11
584
0
          if(cfg_get(tcp, tcp_cfg, accept_no_cl) != 0)
585
0
            tcp_http11_continue(c);
586
0
#endif
587
0
          if(TCP_REQ_HAS_CLEN(r)) {
588
0
            r->body = p + 1;
589
0
            r->bytes_to_go = r->content_len;
590
0
            if(r->bytes_to_go == 0) {
591
0
              r->flags |= F_TCP_REQ_COMPLETE;
592
0
              p++;
593
0
              goto skip;
594
0
            }
595
0
          } else {
596
0
            if(cfg_get(tcp, tcp_cfg, accept_no_cl) != 0) {
597
0
#ifdef READ_MSRP
598
              /* if MSRP message */
599
0
              if(c->req.flags & F_TCP_REQ_MSRP_FRAME) {
600
0
                r->body = p + 1;
601
                /* at least 3 bytes: 0\r\n */
602
0
                r->bytes_to_go = 3;
603
0
                p++;
604
0
                r->content_len = 0;
605
0
                r->state = H_MSRP_BODY;
606
0
                break;
607
0
              }
608
0
#endif
609
610
0
#ifdef READ_HTTP11
611
0
              if(TCP_REQ_BCHUNKED(r)) {
612
0
                r->body = p + 1;
613
                /* at least 3 bytes: 0\r\n */
614
0
                r->bytes_to_go = 3;
615
0
                p++;
616
0
                r->content_len = 0;
617
0
                r->state = H_HTTP11_CHUNK_START;
618
0
                break;
619
0
              }
620
0
#endif
621
0
              r->body = p + 1;
622
0
              r->bytes_to_go = 0;
623
0
              r->flags |= F_TCP_REQ_COMPLETE;
624
0
              p++;
625
0
              goto skip;
626
0
            } else {
627
0
              LM_DBG("no clen, p=%X\n", *p);
628
0
              r->error = TCP_REQ_BAD_LEN;
629
0
            }
630
0
          }
631
0
        } else
632
0
          r->state = H_SKIP;
633
0
        p++;
634
0
        break;
635
636
0
      case H_STARTWS:
637
0
        switch(*p) {
638
0
          content_len_beg_case;
639
0
          crlf_default_skip_case;
640
0
        }
641
0
        p++;
642
0
        break;
643
0
      case H_SKIP_EMPTY:
644
0
        switch(*p) {
645
0
          case '\n':
646
0
            break;
647
0
          case '\r':
648
0
            if(cfg_get(tcp, tcp_cfg, crlf_ping)) {
649
0
              r->state = H_SKIP_EMPTY_CR_FOUND;
650
0
              r->start = p;
651
0
            }
652
0
            break;
653
0
          case ' ':
654
0
          case '\t':
655
            /* skip empty lines */
656
0
            break;
657
0
          case 'C':
658
0
          case 'c':
659
0
            r->state = H_CONT_LEN1;
660
0
            r->start = p;
661
0
            break;
662
0
          case 'l':
663
0
          case 'L':
664
            /* short form for Content-Length */
665
0
            r->state = H_L_COLON;
666
0
            r->start = p;
667
0
            break;
668
0
          default:
669
            /* stun test */
670
0
            if(unlikely(sr_event_enabled(SREV_STUN_IN))
671
0
                && (unsigned char)*p == 0x00) {
672
0
              r->state = H_STUN_MSG;
673
              /* body is used as pointer to the last used byte */
674
0
              r->body = p;
675
0
              r->content_len = 0;
676
0
              LM_DBG("stun msg detected\n");
677
0
            } else {
678
0
              r->state = H_SKIP;
679
0
            }
680
0
            r->start = p;
681
0
        };
682
0
        p++;
683
0
        break;
684
685
0
      case H_SKIP_EMPTY_CR_FOUND:
686
0
        if(*p == '\n') {
687
0
          r->state = H_SKIP_EMPTY_CRLF_FOUND;
688
0
          p++;
689
0
        } else {
690
0
          r->state = H_SKIP_EMPTY;
691
0
        }
692
0
        break;
693
694
0
      case H_SKIP_EMPTY_CRLF_FOUND:
695
0
        if(*p == '\r') {
696
0
          r->state = H_SKIP_EMPTY_CRLFCR_FOUND;
697
0
          p++;
698
0
        } else {
699
0
          r->state = H_SKIP_EMPTY;
700
0
        }
701
0
        break;
702
703
0
      case H_SKIP_EMPTY_CRLFCR_FOUND:
704
0
        if(*p == '\n') {
705
0
          r->state = H_PING_CRLF;
706
0
          r->flags |=
707
0
              F_TCP_REQ_HAS_CLEN
708
0
              | F_TCP_REQ_COMPLETE; /* hack to avoid error check */
709
0
          p++;
710
0
          goto skip;
711
0
        } else {
712
0
          r->state = H_SKIP_EMPTY;
713
0
        }
714
0
        break;
715
716
0
      case H_STUN_MSG:
717
0
        if((r->pos - r->body) >= sizeof(struct stun_hdr)) {
718
          /* copy second short from buffer where should be body
719
           * length
720
           */
721
0
          memcpy(&body_len, &r->start[sizeof(unsigned short)],
722
0
              sizeof(unsigned short));
723
724
0
          body_len = ntohs(body_len);
725
726
          /* check if there is valid magic cookie */
727
0
          memcpy(&mc, &r->start[sizeof(unsigned int)],
728
0
              sizeof(unsigned int));
729
0
          mc = ntohl(mc);
730
          /* using has_content_len as a flag if there should be
731
           * fingerprint or no
732
           */
733
0
          r->flags |= (mc == MAGIC_COOKIE) ? F_TCP_REQ_HAS_CLEN : 0;
734
735
0
          r->body += sizeof(struct stun_hdr);
736
0
          p = r->body;
737
738
0
          if(body_len > 0) {
739
0
            r->state = H_STUN_READ_BODY;
740
0
          } else {
741
0
            if(is_msg_complete(r) != 0) {
742
0
              goto skip;
743
0
            } else {
744
              /* set content_len to length of fingerprint */
745
0
              body_len = sizeof(struct stun_attr) + 20;
746
              /* 20 is SHA_DIGEST_LENGTH from openssl/sha.h */
747
0
            }
748
0
          }
749
0
          r->content_len = body_len;
750
0
        } else {
751
0
          p = r->pos;
752
0
        }
753
0
        break;
754
755
0
      case H_STUN_READ_BODY:
756
        /* check if the whole body was read */
757
0
        body_len = r->content_len;
758
0
        if((r->pos - r->body) >= body_len) {
759
0
          r->body += body_len;
760
0
          p = r->body;
761
0
          if(is_msg_complete(r) != 0) {
762
0
            r->content_len = 0;
763
0
            goto skip;
764
0
          } else {
765
            /* set content_len to length of fingerprint */
766
0
            body_len = sizeof(struct stun_attr) + 20;
767
            /* 20 is SHA_DIGEST_LENGTH from openssl/sha.h */
768
0
            r->content_len = body_len;
769
0
          }
770
0
        } else {
771
0
          p = r->pos;
772
0
        }
773
0
        break;
774
775
0
      case H_STUN_FP:
776
        /* content_len contains length of fingerprint in this place! */
777
0
        body_len = r->content_len;
778
0
        if((r->pos - r->body) >= body_len) {
779
0
          r->body += body_len;
780
0
          p = r->body;
781
0
          r->state = H_STUN_END;
782
0
          r->flags |=
783
0
              F_TCP_REQ_COMPLETE
784
0
              | F_TCP_REQ_HAS_CLEN; /* hack to avoid error check */
785
0
          r->content_len = 0;
786
0
          goto skip;
787
0
        } else {
788
0
          p = r->pos;
789
0
        }
790
0
        break;
791
792
0
        change_state_case(H_CONT_LEN1, 'O', 'o', H_CONT_LEN2);
793
0
        change_state_case(H_CONT_LEN2, 'N', 'n', H_CONT_LEN3);
794
0
        change_state_case(H_CONT_LEN3, 'T', 't', H_CONT_LEN4);
795
0
        change_state_case(H_CONT_LEN4, 'E', 'e', H_CONT_LEN5);
796
0
        change_state_case(H_CONT_LEN5, 'N', 'n', H_CONT_LEN6);
797
0
        change_state_case(H_CONT_LEN6, 'T', 't', H_CONT_LEN7);
798
0
        change_state_case(H_CONT_LEN7, '-', '_', H_CONT_LEN8);
799
0
        change_state_case(H_CONT_LEN8, 'L', 'l', H_CONT_LEN9);
800
0
        change_state_case(H_CONT_LEN9, 'E', 'e', H_CONT_LEN10);
801
0
        change_state_case(H_CONT_LEN10, 'N', 'n', H_CONT_LEN11);
802
0
        change_state_case(H_CONT_LEN11, 'G', 'g', H_CONT_LEN12);
803
0
        change_state_case(H_CONT_LEN12, 'T', 't', H_CONT_LEN13);
804
0
        change_state_case(H_CONT_LEN13, 'H', 'h', H_L_COLON);
805
806
0
      case H_L_COLON:
807
0
        switch(*p) {
808
0
          case ' ':
809
0
          case '\t':
810
0
            break; /* skip space */
811
0
          case ':':
812
0
            r->state = H_CONT_LEN_BODY;
813
0
            break;
814
0
            crlf_default_skip_case;
815
0
        };
816
0
        p++;
817
0
        break;
818
819
0
      case H_CONT_LEN_BODY:
820
0
        switch(*p) {
821
0
          case ' ':
822
0
          case '\t':
823
0
            break; /* eat space */
824
0
          case '0':
825
0
          case '1':
826
0
          case '2':
827
0
          case '3':
828
0
          case '4':
829
0
          case '5':
830
0
          case '6':
831
0
          case '7':
832
0
          case '8':
833
0
          case '9':
834
0
            r->state = H_CONT_LEN_BODY_PARSE;
835
0
            r->content_len = (*p - '0');
836
0
            break;
837
            /* note: review case of content-length
838
             * on different lines */
839
0
            crlf_default_skip_case;
840
0
        }
841
0
        p++;
842
0
        break;
843
844
0
      case H_CONT_LEN_BODY_PARSE:
845
0
        switch(*p) {
846
0
          case '0':
847
0
          case '1':
848
0
          case '2':
849
0
          case '3':
850
0
          case '4':
851
0
          case '5':
852
0
          case '6':
853
0
          case '7':
854
0
          case '8':
855
0
          case '9':
856
0
            r->content_len = r->content_len * 10 + (*p - '0');
857
0
            break;
858
0
          case '\r':
859
0
          case ' ':
860
0
          case '\t':
861
0
            if(r->content_len < 0) {
862
0
              LM_ERR("bad Content-Length header value %d in"
863
0
                   " state %d\n",
864
0
                  r->content_len, r->state);
865
0
              r->content_len = 0;
866
0
              r->error = TCP_REQ_BAD_LEN;
867
0
              r->state = H_SKIP; /* skip now */
868
0
            }
869
0
            r->state = H_SKIP;
870
0
            r->flags |= F_TCP_REQ_HAS_CLEN;
871
0
            break;
872
0
          case '\n':
873
            /* end of line, parse successful */
874
0
            if(r->content_len < 0) {
875
0
              LM_ERR("bad Content-Length header value %d in"
876
0
                   " state %d\n",
877
0
                  r->content_len, r->state);
878
0
              r->content_len = 0;
879
0
              r->error = TCP_REQ_BAD_LEN;
880
0
              r->state = H_SKIP; /* skip now */
881
0
            }
882
0
            r->state = H_LF;
883
0
            r->flags |= F_TCP_REQ_HAS_CLEN;
884
0
            break;
885
0
          default:
886
0
            LM_ERR("bad Content-Length header value, unexpected "
887
0
                 "char %c in state %d\n",
888
0
                *p, r->state);
889
0
            r->state = H_SKIP; /* try to find another?*/
890
0
        }
891
0
        p++;
892
0
        break;
893
894
0
#ifdef READ_HTTP11
895
0
      case H_HTTP11_CHUNK_START: /* start a new body chunk: SIZE\r\nBODY\r\n */
896
0
        r->chunk_size = 0;
897
0
        r->state = H_HTTP11_CHUNK_SIZE;
898
0
        break;
899
0
      case H_HTTP11_CHUNK_BODY: /* content of chunk */
900
0
        remaining = r->pos - p;
901
0
        if(remaining > r->bytes_to_go)
902
0
          remaining = r->bytes_to_go;
903
0
        r->bytes_to_go -= remaining;
904
0
        p += remaining;
905
0
        if(r->bytes_to_go == 0) {
906
0
          r->state = H_HTTP11_CHUNK_END;
907
          /* shift back body content */
908
0
          if(r->chunk_size > 0 && p - r->chunk_size > r->body) {
909
0
            memmove(r->body + r->content_len, p - r->chunk_size,
910
0
                r->chunk_size);
911
0
            r->content_len += r->chunk_size;
912
0
          }
913
0
          goto skip;
914
0
        }
915
0
        break;
916
917
0
      case H_HTTP11_CHUNK_END:
918
0
        switch(*p) {
919
0
          case '\r':
920
0
          case ' ':
921
0
          case '\t': /* skip */
922
0
            break;
923
0
          case '\n':
924
0
            r->state = H_HTTP11_CHUNK_START;
925
0
            break;
926
0
          default:
927
0
            LM_ERR("bad chunk, unexpected "
928
0
                 "char %c in state %d\n",
929
0
                *p, r->state);
930
0
            r->state = H_SKIP; /* try to find another?*/
931
0
        }
932
0
        p++;
933
0
        break;
934
935
0
      case H_HTTP11_CHUNK_SIZE:
936
0
        switch(*p) {
937
0
          case '0':
938
0
          case '1':
939
0
          case '2':
940
0
          case '3':
941
0
          case '4':
942
0
          case '5':
943
0
          case '6':
944
0
          case '7':
945
0
          case '8':
946
0
          case '9':
947
0
            r->chunk_size <<= 4;
948
0
            r->chunk_size += *p - '0';
949
0
            break;
950
0
          case 'a':
951
0
          case 'b':
952
0
          case 'c':
953
0
          case 'd':
954
0
          case 'e':
955
0
          case 'f':
956
0
            r->chunk_size <<= 4;
957
0
            r->chunk_size += *p - 'a' + 10;
958
0
            break;
959
0
          case 'A':
960
0
          case 'B':
961
0
          case 'C':
962
0
          case 'D':
963
0
          case 'E':
964
0
          case 'F':
965
0
            r->chunk_size <<= 4;
966
0
            r->chunk_size += *p - 'A' + 10;
967
0
            break;
968
0
          case '\r':
969
0
          case ' ':
970
0
          case '\t': /* skip */
971
0
            break;
972
0
          case '\n':
973
            /* end of line, parse successful */
974
0
            r->state = H_HTTP11_CHUNK_BODY;
975
0
            r->bytes_to_go = r->chunk_size;
976
0
            if(r->bytes_to_go == 0) {
977
0
              r->state = H_HTTP11_CHUNK_FINISH;
978
0
              r->flags |= F_TCP_REQ_COMPLETE;
979
0
              p++;
980
0
              goto skip;
981
0
            }
982
0
            break;
983
0
          default:
984
0
            LM_ERR("bad chunk size value, unexpected "
985
0
                 "char %c in state %d\n",
986
0
                *p, r->state);
987
0
            r->state = H_SKIP; /* try to find another?*/
988
0
        }
989
0
        p++;
990
0
        break;
991
0
#endif
992
0
#ifdef READ_MSRP
993
0
      case H_MSRP_BODY: /* body of msrp frame */
994
        /* find lf, we are in this state if we are not interested
995
         * in anything till end of line*/
996
0
        r->flags |= F_TCP_REQ_MSRP_BODY;
997
0
        p = q_memchr(p, '\n', r->pos - p);
998
0
        if(p) {
999
0
          p++;
1000
0
          r->state = H_MSRP_BODY_LF;
1001
0
        } else {
1002
0
          p = r->pos;
1003
0
        }
1004
0
        break;
1005
0
      case H_MSRP_BODY_LF: /* LF in body of msrp frame */
1006
0
        switch(*p) {
1007
0
          case '-':
1008
0
            p--;
1009
0
            r->state = H_MSRP_BODY_END;
1010
0
            break;
1011
0
          default:
1012
0
            r->state = H_MSRP_BODY;
1013
0
        }
1014
0
        p++;
1015
0
        break;
1016
0
      case H_MSRP_BODY_END: /* end of body for msrp frame */
1017
        /* find LF and check if it is end-line */
1018
0
        p = q_memchr(p, '\n', r->pos - p);
1019
0
        if(p) {
1020
          /* check if it is end line '-------sessid$\r\n' */
1021
0
          if(r->pos - r->start < 10) {
1022
0
            LM_ERR("weird situation when reading MSRP frame"
1023
0
                 " - continue reading\n");
1024
            /* *p=='\n' */
1025
0
            r->state = H_MSRP_BODY_LF;
1026
0
            p++;
1027
0
            break;
1028
0
          }
1029
0
          if(*(p - 1) != '\r') {
1030
            /* not ending in '\r\n' - not end-line */
1031
            /* *p=='\n' */
1032
0
            r->state = H_MSRP_BODY_LF;
1033
0
            p++;
1034
0
            break;
1035
0
          }
1036
          /* locate transaction id in first line
1037
           * -- first line exists, that's why we are here */
1038
0
          mfline = q_memchr(r->start, '\n', r->pos - r->start);
1039
0
          mtransid.s = q_memchr(
1040
0
              r->start + 5 /* 'MSRP ' */, ' ', mfline - r->start);
1041
0
          mtransid.len = mtransid.s - r->start - 5;
1042
0
          mtransid.s = r->start + 5;
1043
0
          trim(&mtransid);
1044
0
          if(memcmp(mtransid.s,
1045
0
                 p - 1 /*\r*/ - 1 /* '+'|'#'|'$' */
1046
0
                     - mtransid.len,
1047
0
                 mtransid.len)
1048
0
              != 0) {
1049
            /* no match on session id - not end-line */
1050
            /* *p=='\n' */
1051
0
            r->state = H_MSRP_BODY_LF;
1052
0
            p++;
1053
0
            break;
1054
0
          }
1055
0
          if(memcmp(p - 1 /*\r*/ - 1 /* '+'|'#'|'$' */ - mtransid.len
1056
0
                     - 7 /* 7 x '-' */ - 1 /* '\n' */,
1057
0
                 "\n-------", 8)
1058
0
              != 0) {
1059
            /* no match on "\n-------" - not end-line */
1060
            /* *p=='\n' */
1061
0
            r->state = H_MSRP_BODY_LF;
1062
0
            p++;
1063
0
            break;
1064
0
          }
1065
0
          r->state = H_MSRP_FINISH;
1066
0
          r->flags |= F_TCP_REQ_COMPLETE;
1067
0
          p++;
1068
0
          goto skip;
1069
1070
0
        } else {
1071
0
          p = r->pos;
1072
0
        }
1073
0
        break;
1074
0
#endif
1075
1076
0
      default:
1077
0
        LM_CRIT("unexpected state %d\n", r->state);
1078
0
        abort();
1079
0
    }
1080
0
  }
1081
0
skip:
1082
0
  r->parsed = p;
1083
0
  return bytes;
1084
0
}
1085
1086
1087
#ifdef READ_MSRP
1088
int msrp_process_msg(char *tcpbuf, unsigned int len,
1089
    struct receive_info *rcv_info, struct tcp_connection *con)
1090
0
{
1091
0
  int ret;
1092
0
  tcp_event_info_t tev;
1093
0
  sr_event_param_t evp = {0};
1094
1095
0
  ret = 0;
1096
0
  LM_DBG("MSRP Message: [[>>>\n%.*s<<<]]\n", len, tcpbuf);
1097
0
  if(likely(sr_event_enabled(SREV_TCP_MSRP_FRAME))) {
1098
0
    memset(&tev, 0, sizeof(tcp_event_info_t));
1099
0
    tev.type = SREV_TCP_MSRP_FRAME;
1100
0
    tev.buf = tcpbuf;
1101
0
    tev.len = len;
1102
0
    tev.rcv = rcv_info;
1103
0
    tev.con = con;
1104
0
    evp.data = (void *)(&tev);
1105
0
    ret = sr_event_exec(SREV_TCP_MSRP_FRAME, &evp);
1106
0
  } else {
1107
0
    LM_DBG("no callback registering for handling MSRP - dropping!\n");
1108
0
  }
1109
0
  return ret;
1110
0
}
1111
#endif
1112
1113
#ifdef READ_WS
1114
static int tcp_read_ws(struct tcp_connection *c, rd_conn_flags_t *read_flags)
1115
0
{
1116
0
  int bytes;
1117
0
  uint32_t size, pos, mask_present, len;
1118
0
  char *p;
1119
0
  struct tcp_req *r;
1120
1121
0
  r = &c->req;
1122
0
#ifdef USE_TLS
1123
0
  if(unlikely(c->type == PROTO_WSS))
1124
0
    bytes = tls_read(c, read_flags);
1125
0
  else
1126
0
#endif
1127
0
    bytes = tcp_read(c, read_flags);
1128
1129
0
  if(bytes < 0) {
1130
    /* read error */
1131
0
    return bytes;
1132
0
  }
1133
0
  if(r->parsed == r->pos) {
1134
    /* nothing else to parse */
1135
0
    return bytes;
1136
0
  }
1137
0
  if(r->parsed > r->pos) {
1138
0
    LM_ERR("req buf pos (%p) before parsed (%p) [%d]\n", r->pos, r->parsed,
1139
0
        bytes);
1140
0
    return -1;
1141
0
  }
1142
0
  if(r->pos > r->buf + r->b_size) {
1143
0
    LM_ERR("req pos (%p) over buf (%p / %u) - parsed (%p) [%d]\n", r->pos,
1144
0
        r->buf, r->b_size, r->parsed, bytes);
1145
0
    return -1;
1146
0
  }
1147
0
  if(r->buf > r->parsed) {
1148
0
    LM_ERR("req parsed (%p) before buf (%p / %u) - pos (%p) [%d]\n",
1149
0
        r->parsed, r->buf, r->b_size, r->pos, bytes);
1150
0
    return -1;
1151
0
  }
1152
1153
0
  size = r->pos - r->parsed;
1154
1155
0
  p = r->parsed;
1156
0
  pos = 0;
1157
1158
  /*
1159
   0                   1                   2                   3
1160
   0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
1161
  +-+-+-+-+-------+-+-------------+-------------------------------+
1162
  |F|R|R|R| opcode|M| Payload len |    Extended payload length    |
1163
  |I|S|S|S|  (4)  |A|     (7)     |             (16/64)           |
1164
  |N|V|V|V|       |S|             |   (if payload len==126/127)   |
1165
  | |1|2|3|       |K|             |                               |
1166
  +-+-+-+-+-------+-+-------------+ - - - - - - - - - - - - - - - +
1167
  |     Extended payload length continued, if payload len == 127  |
1168
  + - - - - - - - - - - - - - - - +-------------------------------+
1169
  |                               |Masking-key, if MASK set to 1  |
1170
  +-------------------------------+-------------------------------+
1171
  | Masking-key (continued)       |          Payload Data         |
1172
  +-------------------------------- - - - - - - - - - - - - - - - +
1173
  :                     Payload Data continued ...                :
1174
  + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +
1175
  |                     Payload Data continued ...                |
1176
  +---------------------------------------------------------------+
1177
1178
  Do minimal parse required to make sure the full message has been
1179
  received (websocket module will do full parse and validation).
1180
  */
1181
1182
  /* Process first two bytes */
1183
0
  if(size < pos + 2)
1184
0
    goto skip;
1185
0
  pos++;
1186
0
  mask_present = p[pos] & 0x80;
1187
0
  len = (p[pos] & 0xff) & ~0x80;
1188
0
  pos++;
1189
1190
  /* Work out real length */
1191
0
  if(len == 126) {
1192
    /* 2 bytes store the payload size */
1193
0
    if(size < pos + 2)
1194
0
      goto skip;
1195
1196
0
    len = ((p[pos + 0] & 0xff) << 8) | ((p[pos + 1] & 0xff) << 0);
1197
0
    pos += 2;
1198
0
  } else if(len == 127) {
1199
    /* 8 bytes store the payload size */
1200
0
    if(size < pos + 8) {
1201
0
      goto skip;
1202
0
    }
1203
1204
    /* Only decoding the last four bytes of the length...
1205
       This limits the size of WebSocket messages that can be
1206
       handled to 2^32 - which should be plenty for SIP! */
1207
0
    if((p[pos] & 0xff) != 0 || (p[pos + 1] & 0xff) != 0
1208
0
        || (p[pos + 2] & 0xff) != 0 || (p[pos + 3] & 0xff) != 0) {
1209
0
      LM_WARN("advertised length is too large (more than 2^32)\n");
1210
0
      goto skip;
1211
0
    }
1212
0
    len = ((p[pos + 4] & 0xff) << 24) | ((p[pos + 5] & 0xff) << 16)
1213
0
        | ((p[pos + 6] & 0xff) << 8) | ((p[pos + 7] & 0xff) << 0);
1214
0
    pos += 8;
1215
0
  }
1216
1217
  /* Skip mask */
1218
0
  if(mask_present) {
1219
0
    if(size < pos + 4)
1220
0
      goto skip;
1221
0
    pos += 4;
1222
0
  }
1223
1224
  /* check if advertised length fits in read buffer */
1225
0
  if(len >= r->b_size) {
1226
0
    LM_WARN("advertised length (%u) greater than buffer size (%u)\n", len,
1227
0
        r->b_size);
1228
0
    goto skip;
1229
0
  }
1230
  /* Now check the whole message has been received */
1231
0
  if(size < pos + len)
1232
0
    goto skip;
1233
1234
0
  pos += len;
1235
0
  r->flags |= F_TCP_REQ_COMPLETE;
1236
0
  r->parsed = &p[pos];
1237
1238
0
skip:
1239
0
  return bytes;
1240
0
}
1241
1242
static int ws_process_msg(char *tcpbuf, unsigned int len,
1243
    struct receive_info *rcv_info, struct tcp_connection *con)
1244
0
{
1245
0
  int ret;
1246
0
  tcp_event_info_t tev;
1247
0
  sr_event_param_t evp = {0};
1248
1249
0
  ret = 0;
1250
0
  LM_DBG("WebSocket Message: [[>>>\n%.*s<<<]]\n", len, tcpbuf);
1251
0
  if(likely(sr_event_enabled(SREV_TCP_WS_FRAME_IN))) {
1252
0
    memset(&tev, 0, sizeof(tcp_event_info_t));
1253
0
    tev.type = SREV_TCP_WS_FRAME_IN;
1254
0
    tev.buf = tcpbuf;
1255
0
    tev.len = len;
1256
0
    tev.rcv = rcv_info;
1257
0
    tev.con = con;
1258
0
    evp.data = (void *)(&tev);
1259
0
    ret = sr_event_exec(SREV_TCP_WS_FRAME_IN, &evp);
1260
0
  } else {
1261
0
    LM_DBG("no callback registering for handling WebSockets - dropping!\n");
1262
0
  }
1263
0
  return ret;
1264
0
}
1265
#endif
1266
1267
static int tcp_read_hep3(struct tcp_connection *c, rd_conn_flags_t *read_flags)
1268
0
{
1269
0
  int bytes;
1270
0
  uint32_t size, len;
1271
0
  char *p;
1272
0
  struct tcp_req *r;
1273
1274
0
  r = &c->req;
1275
0
#ifdef USE_TLS
1276
0
  if(unlikely(c->type == PROTO_TLS)) {
1277
0
    bytes = tls_read(c, read_flags);
1278
0
  } else {
1279
0
#endif
1280
0
    bytes = tcp_read(c, read_flags);
1281
0
#ifdef USE_TLS
1282
0
  }
1283
0
#endif
1284
1285
0
  if(bytes <= 0) {
1286
0
    if(likely(r->parsed >= r->pos)) {
1287
0
      LM_DBG("no new bytes to read, but still unparsed content\n");
1288
0
      return 0;
1289
0
    }
1290
0
  }
1291
1292
0
  size = r->pos - r->parsed;
1293
1294
0
  p = r->parsed;
1295
1296
  /* Process first six bytes (HEP3 + 2 bytes the size)*/
1297
0
  if(size < 6) {
1298
0
    LM_DBG("not enough bytes to parse (%u)\n", size);
1299
0
    goto skip;
1300
0
  }
1301
1302
0
  if(p[0] != 'H' || p[1] != 'E' || p[2] != 'P' || p[3] != '3') {
1303
    /* not hep3 */
1304
0
    LM_DBG("not HEP3 packet header (%u): %c %c %c %c / %x %x %x %x\n", size,
1305
0
        p[0], p[1], p[2], p[3], p[0], p[1], p[2], p[3]);
1306
0
    goto skip;
1307
0
  }
1308
0
  r->flags |= F_TCP_REQ_HEP3;
1309
1310
0
  len = ((uint32_t)(p[4] & 0xff) << 8) + (p[5] & 0xff);
1311
1312
  /* check if advertised length fits in read buffer */
1313
0
  if(len >= r->b_size) {
1314
0
    LM_WARN("advertised length (%u) greater than buffer size (%u)\n", len,
1315
0
        r->b_size);
1316
0
    goto skip;
1317
0
  }
1318
  /* check the whole message has been received */
1319
0
  if(size < len) {
1320
0
    LM_DBG("incomplete HEP3 packet (%u / %u)\n", len, size);
1321
0
    goto skip;
1322
0
  }
1323
1324
0
  r->flags |= F_TCP_REQ_COMPLETE;
1325
0
  r->parsed = p + len;
1326
0
  LM_DBG("reading of HEP3 packet is complete (%u / %u)\n", len, size);
1327
1328
0
skip:
1329
0
  return bytes;
1330
0
}
1331
1332
static int hep3_process_msg(char *tcpbuf, unsigned int len,
1333
    struct receive_info *rcv_info, struct tcp_connection *con)
1334
0
{
1335
0
  sip_msg_t msg;
1336
0
  int ret;
1337
0
  sr_event_param_t evp = {0};
1338
1339
0
  memset(&msg, 0, sizeof(sip_msg_t)); /* init everything to 0 */
1340
  /* fill in msg */
1341
0
  msg.buf = tcpbuf;
1342
0
  msg.len = len;
1343
  /* zero termination (termination of orig message below not that
1344
   * useful as most of the work is done with scratch-pad; -jiri  */
1345
  /* buf[len]=0; */ /* WARNING: zero term removed! */
1346
0
  msg.rcv = *rcv_info;
1347
0
  msg.id = msg_no;
1348
0
  msg.pid = my_pid();
1349
0
  msg.set_global_address = default_global_address;
1350
0
  msg.set_global_port = default_global_port;
1351
1352
0
  if(likely(sr_msg_time == 1))
1353
0
    msg_set_time(&msg);
1354
0
  evp.data = (void *)(&msg);
1355
0
  ret = sr_event_exec(SREV_RCV_NOSIP, &evp);
1356
0
  LM_DBG("running hep3 handling event returned %d\n", ret);
1357
0
  if(ret == NONSIP_MSG_DROP) {
1358
0
    free_sip_msg(&msg);
1359
0
    return 0;
1360
0
  }
1361
0
  if(ret < 0) {
1362
0
    LM_ERR("error running hep3 handling event: %d\n", ret);
1363
0
    free_sip_msg(&msg);
1364
0
    return -1;
1365
0
  }
1366
1367
0
  ret = receive_msg(msg.buf, msg.len, &msg.rcv);
1368
0
  LM_DBG("running hep3-enclosed sip request route returned %d\n", ret);
1369
0
  free_sip_msg(&msg);
1370
1371
0
  return ret;
1372
0
}
1373
1374
/**
1375
 * @brief wrapper around receive_msg() to clone the tcpbuf content
1376
 *
1377
 * When receiving over TCP, tcpbuf points inside the TCP stream buffer, but during
1378
 * processing of config, msg->buf content might be changed and may corrupt
1379
 * the content of the stream. Safer, make a clone of buf content in a local
1380
 * buffer and give that to receive_msg() to link to msg->buf
1381
 */
1382
int receive_tcp_msg(char *tcpbuf, unsigned int len,
1383
    struct receive_info *rcv_info, struct tcp_connection *con)
1384
0
{
1385
0
  int ret = 0;
1386
0
#ifdef TCP_CLONE_RCVBUF
1387
0
  static char *buf = NULL;
1388
0
  static unsigned int bsize = 0;
1389
0
  int blen;
1390
1391
  /* cloning is disabled via parameter */
1392
0
  if(likely(tcp_clone_rcvbuf == 0)) {
1393
0
#ifdef READ_MSRP
1394
0
    if(unlikely(con->req.flags & F_TCP_REQ_MSRP_FRAME))
1395
0
      return msrp_process_msg(tcpbuf, len, rcv_info, con);
1396
0
#endif
1397
0
#ifdef READ_WS
1398
0
    if(unlikely(con->type == PROTO_WS || con->type == PROTO_WSS))
1399
0
      return ws_process_msg(tcpbuf, len, rcv_info, con);
1400
0
#endif
1401
0
    if(unlikely(con->req.flags & F_TCP_REQ_HEP3))
1402
0
      return hep3_process_msg(tcpbuf, len, rcv_info, con);
1403
1404
0
    ret = receive_msg(tcpbuf, len, rcv_info);
1405
0
    if(ksr_tcp_script_mode & TCP_SCRIPT_MODE_CONTINUE) {
1406
0
      return 0;
1407
0
    }
1408
0
    return ret;
1409
0
  }
1410
1411
  /* min buffer size is BUF_SIZE */
1412
0
  blen = len;
1413
0
  if(blen < BUF_SIZE)
1414
0
    blen = BUF_SIZE;
1415
1416
  /* allocate buffer when needed
1417
   * - no buffer yet
1418
   * - existing buffer too small (min size is BUF_SIZE - to accommodate most
1419
   *   of SIP messages; expected larger for HTTP/XCAP)
1420
   * - existing buffer too large (e.g., we got a too big message in the past,
1421
   *   let's free it)
1422
   *
1423
   * - also, use system memory, not to eat from PKG (same as static buffer
1424
   *   from PKG pov)
1425
   */
1426
0
  if(buf == NULL || bsize < blen || blen < bsize / 2) {
1427
0
    if(buf != NULL)
1428
0
      free(buf);
1429
0
    buf = malloc(blen + 1);
1430
0
    if(buf == 0) {
1431
0
      SYS_MEM_ERROR;
1432
0
      return -1;
1433
0
    }
1434
0
    bsize = blen;
1435
0
  }
1436
1437
0
  memcpy(buf, tcpbuf, len);
1438
0
  buf[len] = '\0';
1439
0
#ifdef READ_MSRP
1440
0
  if(unlikely(con->req.flags & F_TCP_REQ_MSRP_FRAME))
1441
0
    return msrp_process_msg(buf, len, rcv_info, con);
1442
0
#endif
1443
0
#ifdef READ_WS
1444
0
  if(unlikely(con->type == PROTO_WS || con->type == PROTO_WSS))
1445
0
    return ws_process_msg(buf, len, rcv_info, con);
1446
0
#endif
1447
0
  if(unlikely(con->req.flags & F_TCP_REQ_HEP3))
1448
0
    return hep3_process_msg(tcpbuf, len, rcv_info, con);
1449
0
  ret = receive_msg(buf, len, rcv_info);
1450
0
  if(ksr_tcp_script_mode & TCP_SCRIPT_MODE_CONTINUE) {
1451
0
    return 0;
1452
0
  }
1453
0
  return ret;
1454
#else /* TCP_CLONE_RCVBUF */
1455
#ifdef READ_MSRP
1456
  if(unlikely(con->req.flags & F_TCP_REQ_MSRP_FRAME))
1457
    return msrp_process_msg(tcpbuf, len, rcv_info, con);
1458
#endif
1459
#ifdef READ_WS
1460
  if(unlikely(con->type == PROTO_WS || con->type == PROTO_WSS))
1461
    return ws_process_msg(tcpbuf, len, rcv_info, con);
1462
#endif
1463
  if(unlikely(con->req.flags & F_TCP_REQ_HEP3))
1464
    return hep3_process_msg(tcpbuf, len, rcv_info, con);
1465
  ret = receive_msg(tcpbuf, len, rcv_info);
1466
  if(ksr_tcp_script_mode & TCP_SCRIPT_MODE_CONTINUE) {
1467
    return 0;
1468
  }
1469
  return ret;
1470
#endif /* TCP_CLONE_RCVBUF */
1471
0
}
1472
1473
int tcp_read_req(struct tcp_connection *con, int *bytes_read,
1474
    rd_conn_flags_t *read_flags)
1475
0
{
1476
0
  int bytes;
1477
0
  int total_bytes;
1478
0
  int resp;
1479
0
  long size;
1480
0
  struct tcp_req *req;
1481
0
  struct dest_info dst;
1482
0
  char c;
1483
0
  int ret;
1484
1485
0
  bytes = -1;
1486
0
  total_bytes = 0;
1487
0
  resp = CONN_RELEASE;
1488
0
  req = &con->req;
1489
0
  if(req->tvrstart.tv_sec == 0) {
1490
0
    gettimeofday(&req->tvrstart, NULL);
1491
0
  }
1492
1493
0
again:
1494
0
  if(likely(req->error == TCP_REQ_OK)) {
1495
0
#ifdef READ_WS
1496
0
    if(unlikely(con->type == PROTO_WS || con->type == PROTO_WSS)) {
1497
0
      bytes = tcp_read_ws(con, read_flags);
1498
0
    } else {
1499
0
#endif
1500
0
      if(unlikely(ksr_tcp_accept_hep3 != 0)) {
1501
0
        bytes = tcp_read_hep3(con, read_flags);
1502
0
        if(bytes >= 0) {
1503
0
          if(!(con->req.flags & F_TCP_REQ_HEP3)) {
1504
            /* not hep3, try to read headers */
1505
0
            bytes = tcp_read_headers(con, read_flags);
1506
0
          }
1507
0
        }
1508
0
      } else {
1509
0
        bytes = tcp_read_headers(con, read_flags);
1510
0
      }
1511
0
#ifdef READ_WS
1512
0
    }
1513
0
#endif
1514
1515
0
    if(ksr_msg_recv_max_size <= (int)(req->parsed - req->start)) {
1516
0
      LOG(cfg_get(core, core_cfg, corelog),
1517
0
          "read message too large: %d - c: %p r: %p (%d)\n",
1518
0
          (int)(req->parsed - req->start), con, req, bytes);
1519
0
      resp = CONN_ERROR;
1520
0
      goto end_req;
1521
0
    }
1522
1523
0
    if(unlikely(bytes < 0)) {
1524
0
      LOG(cfg_get(core, core_cfg, corelog),
1525
0
          "ERROR: tcp_read_req: error reading - c: %p r: %p (%d)\n",
1526
0
          con, req, bytes);
1527
0
      resp = CONN_ERROR;
1528
0
      goto end_req;
1529
0
    }
1530
1531
#ifdef EXTRA_DEBUG
1532
    /* if timeout state=0; goto end__req; */
1533
    LM_DBG("read= %d bytes, parsed=%d, state=%d, error=%d\n", bytes,
1534
        (int)(req->parsed - req->start), req->state, req->error);
1535
    LM_DBG("last char=0x%02X, parsed msg=\n%.*s\n", *(req->parsed - 1),
1536
        (int)(req->parsed - req->start), req->start);
1537
#endif
1538
0
    total_bytes += bytes;
1539
    /* eof check:
1540
       * is EOF if eof on fd and req.  not complete yet,
1541
       * if req. is complete we might have a second unparsed
1542
       * request after it, so postpone release_with_eof
1543
       */
1544
0
    if(unlikely((con->state == S_CONN_EOF) && (!TCP_REQ_COMPLETE(req)))) {
1545
0
      LM_DBG("EOF\n");
1546
0
      resp = CONN_EOF;
1547
0
      goto end_req;
1548
0
    }
1549
0
  }
1550
0
  if(unlikely(req->error != TCP_REQ_OK)) {
1551
0
    if(req->buf != NULL && req->start != NULL && req->pos != NULL
1552
0
        && req->pos >= req->buf && req->parsed >= req->start) {
1553
0
      LM_ERR("bad request, state=%d, error=%d "
1554
0
           "buf:\n%.*s\nparsed:\n%.*s\n",
1555
0
          req->state, req->error, (int)(req->pos - req->buf),
1556
0
          req->buf, (int)(req->parsed - req->start), req->start);
1557
0
    } else {
1558
0
      LM_ERR("bad request, state=%d, error=%d buf:%d - %p,"
1559
0
           " parsed:%d - %p\n",
1560
0
          req->state, req->error, (int)(req->pos - req->buf),
1561
0
          req->buf, (int)(req->parsed - req->start), req->start);
1562
0
    }
1563
0
    LM_DBG("received from: port %d\n", con->rcv.src_port);
1564
0
    print_ip("received from: ip", &con->rcv.src_ip, "\n");
1565
0
    resp = CONN_ERROR;
1566
0
    goto end_req;
1567
0
  }
1568
0
  if(likely(TCP_REQ_COMPLETE(req))) {
1569
#ifdef EXTRA_DEBUG
1570
    LM_DBG("end of header part\n");
1571
    LM_DBG("received from: port %d\n", con->rcv.src_port);
1572
    print_ip("received from: ip", &con->rcv.src_ip, "\n");
1573
    LM_DBG("headers:\n%.*s.\n", (int)(req->body - req->start), req->start);
1574
#endif
1575
0
    if(likely(TCP_REQ_HAS_CLEN(req))) {
1576
0
      LM_DBG("content-length=%d\n", req->content_len);
1577
#ifdef EXTRA_DEBUG
1578
      LM_DBG("body:\n%.*s\n", req->content_len, req->body);
1579
#endif
1580
0
    } else {
1581
0
      if(cfg_get(tcp, tcp_cfg, accept_no_cl) == 0) {
1582
0
        req->error = TCP_REQ_BAD_LEN;
1583
0
        LM_ERR("content length not present or unparsable\n");
1584
0
        resp = CONN_ERROR;
1585
0
        goto end_req;
1586
0
      }
1587
0
    }
1588
    /* if we are here everything is nice and ok*/
1589
0
    resp = CONN_RELEASE;
1590
0
    if(req->state != H_PING_CRLF) {
1591
0
      req->dxstate |= KSR_TCP_REQSTATE_DATARECV;
1592
0
    }
1593
#ifdef EXTRA_DEBUG
1594
    LM_DBG("receiving msg(%p, %d)\n", req->start,
1595
        (int)(req->parsed - req->start));
1596
#endif
1597
    /* rcv.bind_address should always be !=0 */
1598
0
    bind_address = con->rcv.bind_address;
1599
1600
0
    con->rcv.proto_reserved1 = con->id; /* copy the id */
1601
0
    c = *req->parsed; /* ugly hack: zero term the msg & save the
1602
                 previous char, req->parsed should be ok
1603
                 because we always alloc BUF_SIZE+1 */
1604
0
    *req->parsed = 0;
1605
1606
0
    if(req->state == H_PING_CRLF) {
1607
0
      init_dst_from_rcv(&dst, &con->rcv);
1608
1609
0
      if(tcp_send(&dst, 0, CRLF, CRLF_LEN) < 0) {
1610
0
        LM_ERR("CRLF ping: tcp_send() failed ([%s]:%u -> [%s]:%u)\n",
1611
0
            ip_addr2a(&con->rcv.src_ip), con->rcv.src_port,
1612
0
            ip_addr2a(&con->rcv.dst_ip), con->rcv.dst_port);
1613
0
      }
1614
0
      ret = 0;
1615
0
    } else if(unlikely(req->state == H_STUN_END)) {
1616
      /* stun request */
1617
0
      ret = stun_process_msg(
1618
0
          req->start, req->parsed - req->start, &con->rcv);
1619
0
    } else
1620
0
#ifdef READ_MSRP
1621
      // if (unlikely(req->flags&F_TCP_REQ_MSRP_FRAME)){
1622
0
      if(unlikely(req->state == H_MSRP_FINISH)) {
1623
        /* msrp frame */
1624
0
        ret = receive_tcp_msg(
1625
0
            req->start, req->parsed - req->start, &con->rcv, con);
1626
0
      } else
1627
0
#endif
1628
0
#ifdef READ_HTTP11
1629
0
          if(unlikely(req->state == H_HTTP11_CHUNK_FINISH)) {
1630
        /* http chunked request */
1631
0
        req->body[req->content_len] = 0;
1632
0
        ret = receive_tcp_msg(req->start,
1633
0
            req->body + req->content_len - req->start, &con->rcv,
1634
0
            con);
1635
0
      } else
1636
0
#endif
1637
0
#ifdef READ_WS
1638
0
          if(unlikely(con->type == PROTO_WS
1639
0
                || con->type == PROTO_WSS)) {
1640
0
        ret = receive_tcp_msg(
1641
0
            req->start, req->parsed - req->start, &con->rcv, con);
1642
0
      } else
1643
0
#endif
1644
0
        ret = receive_tcp_msg(
1645
0
            req->start, req->parsed - req->start, &con->rcv, con);
1646
1647
0
    if(unlikely(ret < 0)) {
1648
0
      *req->parsed = c;
1649
0
      resp = CONN_ERROR;
1650
0
      goto end_req;
1651
0
    }
1652
0
    *req->parsed = c;
1653
1654
    /* prepare for next request */
1655
0
    size = req->pos - req->parsed;
1656
0
    req->start = req->buf;
1657
0
    req->body = 0;
1658
0
    req->error = TCP_REQ_OK;
1659
0
    req->state = H_SKIP_EMPTY;
1660
0
    req->flags = 0;
1661
0
    req->content_len = 0;
1662
0
    req->bytes_to_go = 0;
1663
0
    req->pos = req->buf + size;
1664
0
    req->tvrstart.tv_sec = 0;
1665
0
    req->tvrstart.tv_usec = 0;
1666
1667
0
    if(unlikely(size)) {
1668
0
      gettimeofday(&req->tvrstart, NULL);
1669
0
      memmove(req->buf, req->parsed, size);
1670
0
      req->parsed = req->buf; /* fix req->parsed after using it */
1671
#ifdef EXTRA_DEBUG
1672
      LM_DBG("preparing for new request, kept %ld bytes\n", size);
1673
#endif
1674
      /*if we still have some unparsed bytes, try to parse them too*/
1675
0
      goto again;
1676
0
    } else if(unlikely(con->state == S_CONN_EOF)) {
1677
0
      LM_DBG("EOF after reading complete request ([%s]:%u -> [%s]:%u)\n",
1678
0
          ip_addr2a(&con->rcv.src_ip), con->rcv.src_port,
1679
0
          ip_addr2a(&con->rcv.dst_ip), con->rcv.dst_port);
1680
0
      resp = CONN_EOF;
1681
0
    }
1682
0
    req->parsed = req->buf; /* fix req->parsed */
1683
0
  }
1684
1685
0
end_req:
1686
0
  if(likely(bytes_read))
1687
0
    *bytes_read = total_bytes;
1688
0
  return resp;
1689
0
}
1690
1691
1692
void release_tcpconn(struct tcp_connection *c, long state, int unix_sock)
1693
0
{
1694
0
  long response[2];
1695
1696
0
  LM_DBG("releasing con %p, state %ld, fd=%d, id=%d ([%s]:%u -> [%s]:%u)\n",
1697
0
      c, state, c->fd, c->id, ip_addr2a(&c->rcv.src_ip), c->rcv.src_port,
1698
0
      ip_addr2a(&c->rcv.dst_ip), c->rcv.dst_port);
1699
0
  LM_DBG("extra_data %p\n", c->extra_data);
1700
  /* release req & signal the parent */
1701
0
  c->reader_pid = 0; /* reset it */
1702
0
  if(c->fd != -1) {
1703
0
    close(c->fd);
1704
0
    c->fd = -1;
1705
0
  }
1706
  /* errno==EINTR, EWOULDBLOCK a.s.o todo */
1707
0
  response[0] = (long)c;
1708
0
  response[1] = state;
1709
1710
0
  if(tsend_stream(unix_sock, (char *)response, sizeof(response), -1) <= 0)
1711
0
    LM_ERR("tsend_stream failed\n");
1712
0
}
1713
1714
1715
static ticks_t tcpconn_read_timeout(ticks_t t, struct timer_ln *tl, void *data)
1716
0
{
1717
0
  struct tcp_connection *c;
1718
1719
0
  c = (struct tcp_connection *)data;
1720
  /* or (struct tcp...*)(tl-offset(c->timer)) */
1721
1722
0
  if(likely(!(c->state < 0) && TICKS_LT(t, c->timeout))) {
1723
    /* timeout extended, exit */
1724
0
    return (ticks_t)(c->timeout - t);
1725
0
  }
1726
  /* if conn->state is ERROR or BAD => force timeout too */
1727
0
  if(unlikely(io_watch_del(&io_w, c->fd, -1, IO_FD_CLOSING) < 0)) {
1728
0
    LM_ERR("io_watch_del failed for %p"
1729
0
         " id %d fd %d, state %d, flags %x, main fd %d"
1730
0
         " ([%s]:%u -> [%s]:%u)\n",
1731
0
        c, c->id, c->fd, c->state, c->flags, c->s,
1732
0
        ip_addr2a(&c->rcv.src_ip), c->rcv.src_port,
1733
0
        ip_addr2a(&c->rcv.dst_ip), c->rcv.dst_port);
1734
0
  }
1735
0
  if(tcp_conn_lst != NULL) {
1736
0
    tcpconn_listrm(tcp_conn_lst, c, c_next, c_prev);
1737
0
    c->event = TCP_CLOSED_TIMEOUT;
1738
0
    release_tcpconn(
1739
0
        c, (c->state < 0) ? CONN_ERROR : CONN_RELEASE, tcpmain_sock);
1740
0
  }
1741
0
  return 0;
1742
0
}
1743
1744
1745
/* handle io routine, based on the fd_map type
1746
 * (it will be called from io_wait_loop* )
1747
 * params:  fm  - pointer to a fd hash entry
1748
 *          idx - index in the fd_array (or -1 if not known)
1749
 * return: -1 on error, or when we are not interested any more on reads
1750
 *            from this fd (e.g.: we are closing it )
1751
 *          0 on EAGAIN or when by some other way it is known that no more
1752
 *            io events are queued on the fd (the receive buffer is empty).
1753
 *            Useful to detect when there are no more io events queued for
1754
 *            sigio_rt, epoll_et, kqueue.
1755
 *         >0 on successfull read from the fd (when there might be more io
1756
 *            queued -- the receive buffer might still be non-empty)
1757
 */
1758
inline static int handle_io(struct fd_map *fm, short events, int idx)
1759
0
{
1760
0
  int ret;
1761
0
  int n;
1762
0
  rd_conn_flags_t read_flags;
1763
0
  struct tcp_connection *con;
1764
0
  int s;
1765
0
  long resp;
1766
0
  ticks_t t;
1767
0
  fd_map_t *ee = NULL;
1768
1769
  /* update the local config */
1770
0
  cfg_update();
1771
1772
0
  switch(fm->type) {
1773
0
    case F_TCPMAIN:
1774
0
    again:
1775
0
      ret = n = receive_fd(fm->fd, &con, sizeof(con), &s, 0);
1776
0
      LM_DBG("received n=%d con=%p, fd=%d\n", n, con, s);
1777
0
      if(unlikely(n < 0)) {
1778
0
        if(errno == EWOULDBLOCK || errno == EAGAIN) {
1779
0
          ret = 0;
1780
0
          break;
1781
0
        } else if(errno == EINTR)
1782
0
          goto again;
1783
0
        else {
1784
0
          LM_CRIT("read_fd: %s \n", strerror(errno));
1785
0
          abort(); /* big error*/
1786
0
        }
1787
0
      }
1788
0
      if(unlikely(n == 0)) {
1789
0
        LM_ERR("0 bytes read\n");
1790
0
        goto error;
1791
0
      }
1792
0
      if(unlikely(con == 0)) {
1793
0
        LM_CRIT("null pointer\n");
1794
0
        goto error;
1795
0
      }
1796
0
      con->fd = s;
1797
0
      if(unlikely(s == -1)) {
1798
0
        LM_ERR("read_fd: no fd read\n");
1799
0
        goto con_error;
1800
0
      }
1801
0
      con->reader_pid = my_pid();
1802
0
      if(unlikely(con == tcp_conn_lst)) {
1803
0
        LM_CRIT("duplicate connection received: %p, id %d, fd %d, "
1804
0
            "refcnt %d"
1805
0
            " state %d (n=%d)\n",
1806
0
            con, con->id, con->fd, atomic_get(&con->refcnt),
1807
0
            con->state, n);
1808
0
        goto con_error;
1809
0
        break; /* try to recover */
1810
0
      }
1811
0
      if(unlikely(con->state == S_CONN_BAD)) {
1812
0
        LM_WARN("received an already bad connection: %p id %d refcnt "
1813
0
            "%d\n",
1814
0
            con, con->id, atomic_get(&con->refcnt));
1815
0
        goto con_error;
1816
0
      }
1817
      /* if we received the fd there is most likely data waiting to
1818
       * be read => process it first to avoid extra sys calls */
1819
0
      read_flags = ((con->flags & (F_CONN_EOF_SEEN | F_CONN_FORCE_EOF))
1820
0
                 && !(con->flags & F_CONN_OOB_DATA))
1821
0
                 ? RD_CONN_FORCE_EOF
1822
0
                 : 0;
1823
0
#ifdef USE_TLS
1824
0
    repeat_1st_read:
1825
0
#endif /* USE_TLS */
1826
0
      resp = tcp_read_req(con, &n, &read_flags);
1827
0
      if(unlikely(resp < 0)) {
1828
        /* some error occurred, but on the new fd, not on the tcp
1829
         * main fd, so keep the ret value */
1830
0
        if(unlikely(resp != CONN_EOF))
1831
0
          con->state = S_CONN_BAD;
1832
0
        release_tcpconn(con, resp, tcpmain_sock);
1833
0
        break;
1834
0
      }
1835
0
#ifdef USE_TLS
1836
      /* repeat read if requested (for now only tls might do this) */
1837
0
      if(unlikely(read_flags & RD_CONN_REPEAT_READ))
1838
0
        goto repeat_1st_read;
1839
0
#endif /* USE_TLS */
1840
1841
      /* must be before io_watch_add, io_watch_add might catch some
1842
       * already existing events => might call handle_io and
1843
       * handle_io might decide to del. the new connection =>
1844
       * must be in the list */
1845
0
      tcpconn_listadd(tcp_conn_lst, con, c_next, c_prev);
1846
0
      t = get_ticks_raw();
1847
0
      con->timeout = t + S_TO_TICKS(TCP_CHILD_TIMEOUT);
1848
      /* re-activate the timer */
1849
0
      con->timer.f = tcpconn_read_timeout;
1850
0
      local_timer_reinit(&con->timer);
1851
0
      local_timer_add(&tcp_reader_ltimer, &con->timer,
1852
0
          S_TO_TICKS(TCP_CHILD_TIMEOUT), t);
1853
0
      if(unlikely(io_watch_add(&io_w, s, POLLIN, F_TCPCONN, con) < 0)) {
1854
0
        LM_CRIT("io_watch_add failed for %p id %d fd %d, state %d, "
1855
0
            "flags %x,"
1856
0
            " main fd %d, refcnt %d ([%s]:%u -> [%s]:%u)\n",
1857
0
            con, con->id, con->fd, con->state, con->flags, con->s,
1858
0
            atomic_get(&con->refcnt), ip_addr2a(&con->rcv.src_ip),
1859
0
            con->rcv.src_port, ip_addr2a(&con->rcv.dst_ip),
1860
0
            con->rcv.dst_port);
1861
0
        ee = get_fd_map(&io_w, s);
1862
0
        if(ee != 0 && ee->type == F_TCPCONN) {
1863
0
          tcp_connection_t *ec;
1864
0
          ec = (tcp_connection_t *)ee->data;
1865
0
          LM_CRIT("existing tcp con %p id %d fd %d, state %d, flags "
1866
0
              "%x,"
1867
0
              " main fd %d, refcnt %d ([%s]:%u -> [%s]:%u)\n",
1868
0
              ec, ec->id, ec->fd, ec->state, ec->flags, ec->s,
1869
0
              atomic_get(&ec->refcnt), ip_addr2a(&ec->rcv.src_ip),
1870
0
              ec->rcv.src_port, ip_addr2a(&ec->rcv.dst_ip),
1871
0
              ec->rcv.dst_port);
1872
0
        }
1873
0
        if(tcp_conn_lst != NULL) {
1874
0
          tcpconn_listrm(tcp_conn_lst, con, c_next, c_prev);
1875
0
          local_timer_del(&tcp_reader_ltimer, &con->timer);
1876
0
        }
1877
0
        goto con_error;
1878
0
      }
1879
0
      break;
1880
0
    case F_TCPCONN:
1881
0
      con = (struct tcp_connection *)fm->data;
1882
0
      if(unlikely(con->state == S_CONN_BAD)) {
1883
0
        resp = CONN_ERROR;
1884
0
        if(!(con->send_flags.f & SND_F_CON_CLOSE))
1885
0
          LM_WARN("F_TCPCONN connection marked as bad: %p id %d fd %d"
1886
0
              " refcnt %d ([%s]:%u -> [%s]:%u)\n",
1887
0
              con, con->id, con->fd, atomic_get(&con->refcnt),
1888
0
              ip_addr2a(&con->rcv.src_ip), con->rcv.src_port,
1889
0
              ip_addr2a(&con->rcv.dst_ip), con->rcv.dst_port);
1890
0
        goto read_error;
1891
0
      }
1892
0
      read_flags =
1893
0
          ((
1894
0
#ifdef POLLRDHUP
1895
0
               (events & POLLRDHUP) |
1896
0
#endif /* POLLRDHUP */
1897
0
               (events & (POLLHUP | POLLERR))
1898
0
               | (con->flags
1899
0
                   & (F_CONN_EOF_SEEN | F_CONN_FORCE_EOF)))
1900
0
              && !(events & POLLPRI))
1901
0
              ? RD_CONN_FORCE_EOF
1902
0
              : 0;
1903
0
#ifdef USE_TLS
1904
0
    repeat_read:
1905
0
#endif /* USE_TLS */
1906
0
      resp = tcp_read_req(con, &ret, &read_flags);
1907
0
      if(unlikely(resp < 0)) {
1908
0
      read_error:
1909
0
        ret = -1; /* some error occurred */
1910
0
        if(unlikely(io_watch_del(&io_w, con->fd, idx, IO_FD_CLOSING)
1911
0
              < 0)) {
1912
0
          LM_CRIT("io_watch_del failed for %p id %d fd %d,"
1913
0
              " state %d, flags %x, main fd %d, refcnt %d"
1914
0
              " ([%s]:%u -> [%s]:%u)\n",
1915
0
              con, con->id, con->fd, con->state, con->flags,
1916
0
              con->s, atomic_get(&con->refcnt),
1917
0
              ip_addr2a(&con->rcv.src_ip), con->rcv.src_port,
1918
0
              ip_addr2a(&con->rcv.dst_ip), con->rcv.dst_port);
1919
0
        }
1920
0
        if(tcp_conn_lst != NULL) {
1921
0
          LM_DBG("removing from list %p id %d fd %d,"
1922
0
               " state %d, flags %x, main fd %d, refcnt %d"
1923
0
               " ([%s]:%u -> [%s]:%u)\n",
1924
0
              con, con->id, con->fd, con->state, con->flags,
1925
0
              con->s, atomic_get(&con->refcnt),
1926
0
              ip_addr2a(&con->rcv.src_ip), con->rcv.src_port,
1927
0
              ip_addr2a(&con->rcv.dst_ip), con->rcv.dst_port);
1928
0
          tcpconn_listrm(tcp_conn_lst, con, c_next, c_prev);
1929
0
          local_timer_del(&tcp_reader_ltimer, &con->timer);
1930
0
          if(unlikely(resp != CONN_EOF))
1931
0
            con->state = S_CONN_BAD;
1932
0
          release_tcpconn(con, resp, tcpmain_sock);
1933
0
        }
1934
0
      } else {
1935
0
#ifdef USE_TLS
1936
0
        if(unlikely(read_flags & RD_CONN_REPEAT_READ))
1937
0
          goto repeat_read;
1938
0
#endif /* USE_TLS */
1939
        /* update timeout */
1940
0
        con->timeout = get_ticks_raw() + S_TO_TICKS(TCP_CHILD_TIMEOUT);
1941
        /* ret= 0 (read the whole socket buffer) if short read
1942
         * & !POLLPRI,  bytes read otherwise */
1943
0
        ret &= (((read_flags & RD_CONN_SHORT_READ)
1944
0
                && !(events & POLLPRI))
1945
0
            - 1);
1946
0
      }
1947
0
      break;
1948
0
    case F_NONE:
1949
0
      LM_CRIT("empty fd map %p (%d): {%d, %d, %p}\n", fm,
1950
0
          (int)(fm - io_w.fd_hash), fm->fd, fm->type, fm->data);
1951
0
      goto error;
1952
0
    default:
1953
0
      LM_CRIT("unknown fd type %d\n", fm->type);
1954
0
      goto error;
1955
0
  }
1956
1957
0
  return ret;
1958
0
con_error:
1959
0
  con->state = S_CONN_BAD;
1960
0
  release_tcpconn(con, CONN_ERROR, tcpmain_sock);
1961
0
  return ret;
1962
0
error:
1963
0
  return -1;
1964
0
}
1965
1966
1967
inline static void tcp_reader_timer_run(void)
1968
0
{
1969
0
  ticks_t ticks;
1970
1971
0
  ticks = get_ticks_raw();
1972
0
  if(unlikely((ticks - tcp_reader_prev_ticks) < TCPCONN_TIMEOUT_MIN_RUN))
1973
0
    return;
1974
0
  tcp_reader_prev_ticks = ticks;
1975
0
  local_timer_run(&tcp_reader_ltimer, ticks);
1976
0
}
1977
1978
1979
void tcp_receive_loop(int unix_sock)
1980
0
{
1981
1982
  /* init */
1983
0
  tcpmain_sock = unix_sock; /* init com. socket */
1984
0
  if(init_io_wait(&io_w, get_max_open_fds(), tcp_poll_method) < 0)
1985
0
    goto error;
1986
0
  tcp_reader_prev_ticks = get_ticks_raw();
1987
0
  if(init_local_timer(&tcp_reader_ltimer, get_ticks_raw()) != 0)
1988
0
    goto error;
1989
  /* add the unix socket */
1990
0
  if(io_watch_add(&io_w, tcpmain_sock, POLLIN, F_TCPMAIN, 0) < 0) {
1991
0
    LM_CRIT("failed to add tcp main socket to the fd list\n");
1992
0
    goto error;
1993
0
  }
1994
1995
  /* initialize the config framework */
1996
0
  if(cfg_child_init())
1997
0
    goto error;
1998
1999
  /* main loop */
2000
0
  switch(io_w.poll_method) {
2001
0
    case POLL_POLL:
2002
0
      while(1) {
2003
0
        io_wait_loop_poll(&io_w, TCP_CHILD_SELECT_TIMEOUT, 0);
2004
0
        tcp_reader_timer_run();
2005
0
      }
2006
0
      break;
2007
0
#ifdef HAVE_SELECT
2008
0
    case POLL_SELECT:
2009
0
      while(1) {
2010
0
        io_wait_loop_select(&io_w, TCP_CHILD_SELECT_TIMEOUT, 0);
2011
0
        tcp_reader_timer_run();
2012
0
      }
2013
0
      break;
2014
0
#endif
2015
0
#ifdef HAVE_SIGIO_RT
2016
0
    case POLL_SIGIO_RT:
2017
0
      while(1) {
2018
0
        io_wait_loop_sigio_rt(&io_w, TCP_CHILD_SELECT_TIMEOUT);
2019
0
        tcp_reader_timer_run();
2020
0
      }
2021
0
      break;
2022
0
#endif
2023
0
#ifdef HAVE_EPOLL
2024
0
    case POLL_EPOLL_LT:
2025
0
      while(1) {
2026
0
        io_wait_loop_epoll(&io_w, TCP_CHILD_SELECT_TIMEOUT, 0);
2027
0
        tcp_reader_timer_run();
2028
0
      }
2029
0
      break;
2030
0
    case POLL_EPOLL_ET:
2031
0
      while(1) {
2032
0
        io_wait_loop_epoll(&io_w, TCP_CHILD_SELECT_TIMEOUT, 1);
2033
0
        tcp_reader_timer_run();
2034
0
      }
2035
0
      break;
2036
0
#endif
2037
#ifdef HAVE_KQUEUE
2038
    case POLL_KQUEUE:
2039
      while(1) {
2040
        io_wait_loop_kqueue(&io_w, TCP_CHILD_SELECT_TIMEOUT, 0);
2041
        tcp_reader_timer_run();
2042
      }
2043
      break;
2044
#endif
2045
#ifdef HAVE_DEVPOLL
2046
    case POLL_DEVPOLL:
2047
      while(1) {
2048
        io_wait_loop_devpoll(&io_w, TCP_CHILD_SELECT_TIMEOUT, 0);
2049
        tcp_reader_timer_run();
2050
      }
2051
      break;
2052
#endif
2053
0
    default:
2054
0
      LM_CRIT("no support for poll method %s (%d)\n",
2055
0
          poll_method_name(io_w.poll_method), io_w.poll_method);
2056
0
      goto error;
2057
0
  }
2058
0
error:
2059
0
  destroy_io_wait(&io_w);
2060
0
  LM_CRIT("exiting...");
2061
0
  ksr_exit(-1);
2062
0
}
2063
2064
2065
int is_msg_complete(struct tcp_req *r)
2066
0
{
2067
0
  if(TCP_REQ_HAS_CLEN(r)) {
2068
0
    r->state = H_STUN_FP;
2069
0
    return 0;
2070
0
  } else {
2071
    /* STUN message is complete */
2072
0
    r->state = H_STUN_END;
2073
0
    r->flags |= F_TCP_REQ_COMPLETE
2074
0
          | F_TCP_REQ_HAS_CLEN; /* hack to avoid error check */
2075
0
    return 1;
2076
0
  }
2077
0
}
2078
2079
#endif /* USE_TCP */