diff options
author | David M. Lee <dlee@digium.com> | 2013-01-18 05:31:23 +0000 |
---|---|---|
committer | David M. Lee <dlee@digium.com> | 2013-01-18 05:31:23 +0000 |
commit | be727bf0d217ae086f5df3f1a3e3338be7c71a48 (patch) | |
tree | 8396e3281f45a8830b372dc37032938d0b03e8ec /channels/sip/reqresp_parser.c | |
parent | ea78b7cbc8e8806f1d55ba30726a8588391ffb00 (diff) |
Fix Record-Route parsing for large headers.
Record-Route parsing copied the header into a char[256] array, which can
be a problem if the header is longer than that. This patch parses the
header in place, without the copy, avoiding the issue.
In addition to the original patch, I added a unit test for the new
get_in_brackets_const function.
(closes issue ASTERISK-20837)
Reported by: Corey Farrell
Patches:
chan_sip-build_route-optimized-rev1.patch uploaded by Corey Farrell (license 5909)
(with minor changes by dlee)
........
Merged revisions 379392 from http://svn.asterisk.org/svn/asterisk/branches/1.8
........
Merged revisions 379393 from http://svn.asterisk.org/svn/asterisk/branches/11
git-svn-id: https://origsvn.digium.com/svn/asterisk/trunk@379394 65c4cc65-6c06-0410-ace0-fbb531ad65f3
Diffstat (limited to 'channels/sip/reqresp_parser.c')
-rw-r--r-- | channels/sip/reqresp_parser.c | 53 |
1 files changed, 53 insertions, 0 deletions
diff --git a/channels/sip/reqresp_parser.c b/channels/sip/reqresp_parser.c index 7893aace5..9ef4fee17 100644 --- a/channels/sip/reqresp_parser.c +++ b/channels/sip/reqresp_parser.c @@ -948,6 +948,59 @@ AST_TEST_DEFINE(get_name_and_number_test) return res; } +int get_in_brackets_const(const char *src,const char **start,int *length) +{ + const char *parse = src; + const char *first_bracket; + const char *second_bracket; + + if (start == NULL) { + return -1; + } + if (length == NULL) { + return -1; + } + *start = NULL; + *length = -1; + if (ast_strlen_zero(src)) { + return 1; + } + + /* + * Skip any quoted text until we find the part in brackets. + * On any error give up and return -1 + */ + while ( (first_bracket = strchr(parse, '<')) ) { + const char *first_quote = strchr(parse, '"'); + first_bracket++; + if (!first_quote || first_quote >= first_bracket) { + break; /* no need to look at quoted part */ + } + /* the bracket is within quotes, so ignore it */ + parse = find_closing_quote(first_quote + 1, NULL); + if (!*parse) { + ast_log(LOG_WARNING, "No closing quote found in '%s'\n", src); + return -1; + } + parse++; + } + + /* Require a first bracket. Unlike get_in_brackets_full, this procedure is passed a const, + * so it can expect a pointer to an original value */ + if (!first_bracket) { + ast_log(LOG_WARNING, "No opening bracket found in '%s'\n", src); + return 1; + } + + if ((second_bracket = strchr(first_bracket, '>'))) { + *start = first_bracket; + *length = second_bracket - first_bracket; + return 0; + } + ast_log(LOG_WARNING, "No closing bracket found in '%s'\n", src); + return -1; +} + int get_in_brackets_full(char *tmp,char **out,char **residue) { const char *parse = tmp; |