summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--channels/chan_skinny.c122
-rw-r--r--res/res_hep_rtcp.c1
-rw-r--r--third-party/pjproject/patches/0058-Parse-zero-length-multipart-body-parts-correctly.patch41
-rw-r--r--third-party/pjproject/patches/0059-Ensure-2543-transaction-key-buffer-is-large-enough.patch29
4 files changed, 137 insertions, 56 deletions
diff --git a/channels/chan_skinny.c b/channels/chan_skinny.c
index a0530007b..aeb060569 100644
--- a/channels/chan_skinny.c
+++ b/channels/chan_skinny.c
@@ -6658,7 +6658,7 @@ static int handle_capabilities_res_message(struct skinny_req *req, struct skinny
#ifdef AST_DEVMODE
struct ast_str *codec_buf = ast_str_alloca(AST_FORMAT_CAP_NAMES_LEN);
#endif
-
+
if (!codecs) {
return 0;
@@ -7499,6 +7499,8 @@ static void skinny_session_cleanup(void *data)
destroy_session(s);
}
+#define PACKET_TIMEOUT 10000
+
static void *skinny_session(void *data)
{
int res;
@@ -7545,78 +7547,86 @@ static void *skinny_session(void *data)
}
}
- if (fds[0].revents) {
+ if (!fds[0].revents) {
+ continue;
+ }
+ ast_debug(1, "Reading header\n");
- if (!(req = ast_calloc(1, SKINNY_MAX_PACKET))) {
- ast_log(LOG_WARNING, "Unable to allocated memorey for skinny_req.\n");
- break;
- }
+ if (!(req = ast_calloc(1, SKINNY_MAX_PACKET))) {
+ ast_log(LOG_WARNING, "Unable to allocated memorey for skinny_req.\n");
+ break;
+ }
- ast_mutex_lock(&s->lock);
- s->lockstate = 1;
+ ast_mutex_lock(&s->lock);
+ s->lockstate = 1;
- if ((res = read(s->fd, req, skinny_header_size)) != skinny_header_size) {
- if (res < 0) {
- ast_log(LOG_WARNING, "Header read() returned error: %s\n", strerror(errno));
- } else {
- ast_log(LOG_WARNING, "Unable to read header. Only found %d bytes.\n", res);
- }
- break;
+ if ((res = read(s->fd, req, skinny_header_size)) != skinny_header_size) {
+ if (res < 0) {
+ ast_log(LOG_WARNING, "Header read() returned error: %s\n", strerror(errno));
+ } else {
+ ast_log(LOG_WARNING, "Unable to read header. Only found %d bytes.\n", res);
}
+ break;
+ }
- eventmessage = letohl(req->e);
- if (eventmessage < 0) {
- ast_log(LOG_ERROR, "Event Message is NULL from socket %d, This is bad\n", s->fd);
- break;
- }
+ eventmessage = letohl(req->e);
+ if (eventmessage < 0) {
+ ast_log(LOG_ERROR, "Event Message is NULL from socket %d, This is bad\n", s->fd);
+ break;
+ }
- dlen = letohl(req->len) - 4;
- if (dlen < 0) {
- ast_log(LOG_WARNING, "Skinny Client sent invalid data.\n");
- break;
- }
- if (dlen > (SKINNY_MAX_PACKET - skinny_header_size)) {
- ast_log(LOG_WARNING, "Skinny packet too large (%d bytes), max length(%d bytes)\n", dlen+8, SKINNY_MAX_PACKET);
- break;
- }
+ dlen = letohl(req->len) - 4;
+ if (dlen < 0) {
+ ast_log(LOG_WARNING, "Skinny Client sent invalid data.\n");
+ break;
+ }
+ if (dlen > (SKINNY_MAX_PACKET - skinny_header_size)) {
+ ast_log(LOG_WARNING, "Skinny packet too large (%d bytes), max length(%d bytes)\n", dlen+8, SKINNY_MAX_PACKET);
+ break;
+ }
- bytesread = 0;
- while (1) {
- if ((res = read(s->fd, ((char*)&req->data)+bytesread, dlen-bytesread)) < 0) {
- ast_log(LOG_WARNING, "Data read() returned error: %s\n", strerror(errno));
- break;
- }
- bytesread += res;
- if (bytesread >= dlen) {
- if (res < bytesread) {
- ast_log(LOG_WARNING, "Rest of partial data received.\n");
- }
- if (bytesread > dlen) {
- ast_log(LOG_WARNING, "Client sent wrong amount of data (%d), expected (%d).\n", bytesread, dlen);
- res = -1;
- }
- break;
- }
+ ast_debug(1, "Read header: Message ID: 0x%04x, %d bytes in packet\n", eventmessage, dlen);
- ast_log(LOG_WARNING, "Partial data received, waiting (%d bytes read of %d)\n", bytesread, dlen);
- if (sched_yield() < 0) {
- ast_log(LOG_WARNING, "Data yield() returned error: %s\n", strerror(errno));
- res = -1;
- break;
+ bytesread = 0;
+ while (bytesread < dlen) {
+ ast_debug(1, "Waiting %dms for %d bytes of %d\n", PACKET_TIMEOUT, dlen - bytesread, dlen);
+ fds[0].revents = 0;
+ res = ast_poll(fds, 1, PACKET_TIMEOUT);
+ if (res <= 0) {
+ if (res == 0) {
+ ast_debug(1, "Poll timed out waiting for %d bytes\n", dlen - bytesread);
+ } else {
+ ast_log(LOG_WARNING, "Poll failed waiting for %d bytes: %s\n",
+ dlen - bytesread, strerror(errno));
}
+ ast_verb(3, "Ending Skinny session from %s (bad input)\n", ast_inet_ntoa(s->sin.sin_addr));
+ res = -1;
+
+ break;
+ }
+ if (!fds[0].revents) {
+ continue;
}
- s->lockstate = 0;
- ast_mutex_unlock(&s->lock);
+ res = read(s->fd, ((char*)&req->data)+bytesread, dlen-bytesread);
if (res < 0) {
+ ast_log(LOG_WARNING, "Data read() returned error: %s\n", strerror(errno));
break;
}
+ bytesread += res;
+ ast_debug(1, "Read %d bytes. %d of %d now read\n", res, bytesread, dlen);
+ }
- pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, NULL);
- res = handle_message(req, s);
- pthread_setcancelstate(PTHREAD_CANCEL_ENABLE, NULL);
+ s->lockstate = 0;
+ ast_mutex_unlock(&s->lock);
+ if (res < 0) {
+ break;
}
+ pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, NULL);
+ res = handle_message(req, s);
+ pthread_setcancelstate(PTHREAD_CANCEL_ENABLE, NULL);
+
if (req) {
ast_free(req);
req = NULL;
diff --git a/res/res_hep_rtcp.c b/res/res_hep_rtcp.c
index 395031a3d..31b9c485b 100644
--- a/res/res_hep_rtcp.c
+++ b/res/res_hep_rtcp.c
@@ -181,6 +181,7 @@ static int unload_module(void)
}
AST_MODULE_INFO(ASTERISK_GPL_KEY, AST_MODFLAG_LOAD_ORDER, "RTCP HEPv3 Logger",
+ .support_level = AST_MODULE_SUPPORT_EXTENDED,
.load = load_module,
.unload = unload_module,
.load_pri = AST_MODPRI_DEFAULT,
diff --git a/third-party/pjproject/patches/0058-Parse-zero-length-multipart-body-parts-correctly.patch b/third-party/pjproject/patches/0058-Parse-zero-length-multipart-body-parts-correctly.patch
new file mode 100644
index 000000000..49334c354
--- /dev/null
+++ b/third-party/pjproject/patches/0058-Parse-zero-length-multipart-body-parts-correctly.patch
@@ -0,0 +1,41 @@
+From f0c717463d569f87a16f9b014033c8ca8939a7b4 Mon Sep 17 00:00:00 2001
+From: Mark Michelson <mmichelson@digium.com>
+Date: Thu, 13 Apr 2017 16:59:40 -0500
+Subject: [PATCH] Parse zero-length multipart body parts correctly.
+
+The calculation of end_body could result in a negative length being
+passed to multipart_body_parse_part().
+---
+ pjsip/src/pjsip/sip_multipart.c | 16 +++++++++-------
+ 1 file changed, 9 insertions(+), 7 deletions(-)
+
+diff --git a/pjsip/src/pjsip/sip_multipart.c b/pjsip/src/pjsip/sip_multipart.c
+index 8351f7e..b302139 100644
+--- a/pjsip/src/pjsip/sip_multipart.c
++++ b/pjsip/src/pjsip/sip_multipart.c
+@@ -653,13 +653,15 @@ PJ_DEF(pjsip_msg_body*) pjsip_multipart_parse(pj_pool_t *pool,
+
+ end_body = curptr;
+
+- /* The newline preceeding the delimiter is conceptually part of
+- * the delimiter, so trim it from the body.
+- */
+- if (*(end_body-1) == '\n')
+- --end_body;
+- if (*(end_body-1) == '\r')
+- --end_body;
++ if (end_body > start_body) {
++ /* The newline preceeding the delimiter is conceptually part of
++ * the delimiter, so trim it from the body.
++ */
++ if (*(end_body-1) == '\n')
++ --end_body;
++ if (*(end_body-1) == '\r')
++ --end_body;
++ }
+
+ /* Now that we have determined the part's boundary, parse it
+ * to get the header and body part of the part.
+--
+1.9.1
+
diff --git a/third-party/pjproject/patches/0059-Ensure-2543-transaction-key-buffer-is-large-enough.patch b/third-party/pjproject/patches/0059-Ensure-2543-transaction-key-buffer-is-large-enough.patch
new file mode 100644
index 000000000..eb5a7db73
--- /dev/null
+++ b/third-party/pjproject/patches/0059-Ensure-2543-transaction-key-buffer-is-large-enough.patch
@@ -0,0 +1,29 @@
+From b5f0f8868363c482a2c4ce343e3ee6ad256b0708 Mon Sep 17 00:00:00 2001
+From: Mark Michelson <mmichelson@digium.com>
+Date: Thu, 13 Apr 2017 16:20:07 -0500
+Subject: [PATCH] Ensure 2543 transaction key buffer is large enough.
+
+The CSeq method length needs to be factored into the allocated buffer
+length. Otherwise, the buffer may not be large enough to accommodate the
+entire key.
+---
+ pjsip/src/pjsip/sip_transaction.c | 3 ++-
+ 1 file changed, 2 insertions(+), 1 deletion(-)
+
+diff --git a/pjsip/src/pjsip/sip_transaction.c b/pjsip/src/pjsip/sip_transaction.c
+index c1750dc..2200d8d 100644
+--- a/pjsip/src/pjsip/sip_transaction.c
++++ b/pjsip/src/pjsip/sip_transaction.c
+@@ -288,7 +288,8 @@ static pj_status_t create_tsx_key_2543( pj_pool_t *pool,
+ host = &rdata->msg_info.via->sent_by.host;
+
+ /* Calculate length required. */
+- len_required = 9 + /* CSeq number */
++ len_required = method->name.slen + /* Method */
++ 9 + /* CSeq number */
+ rdata->msg_info.from->tag.slen + /* From tag. */
+ rdata->msg_info.cid->id.slen + /* Call-ID */
+ host->slen + /* Via host. */
+--
+1.9.1
+