2 * Routines handling protocols with a request/response line, headers,
3 * a blank line, and an optional body.
5 * $Id: req_resp_hdrs.c,v 1.3 2003/12/29 22:33:18 guy Exp $
7 * Ethereal - Network traffic analyzer
8 * By Gerald Combs <gerald@ethereal.com>
9 * Copyright 1998 Gerald Combs
11 * This program is free software; you can redistribute it and/or
12 * modify it under the terms of the GNU General Public License
13 * as published by the Free Software Foundation; either version 2
14 * of the License, or (at your option) any later version.
16 * This program is distributed in the hope that it will be useful,
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 * GNU General Public License for more details.
21 * You should have received a copy of the GNU General Public License
22 * along with this program; if not, write to the Free Software
23 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
31 #include <epan/packet.h>
32 #include <epan/strutil.h>
34 #include "req_resp_hdrs.h"
37 * Optionally do reassembly of the request/response line, headers, and body.
40 req_resp_hdrs_do_reassembly(tvbuff_t *tvb, packet_info *pinfo,
41 gboolean desegment_headers, gboolean desegment_body)
46 gint length_remaining, reported_length_remaining;
48 long int content_length;
49 gboolean content_length_found = FALSE;
52 * Do header desegmentation if we've been told to.
54 * RFC 2616 defines HTTP messages as being either of the
55 * Request or the Response type
56 * (HTTP-message = Request | Response).
57 * Request and Response are defined as:
58 * Request = Request-Line
61 * | entity-header ) CRLF)
64 * Response = Status-Line
67 * | entity-header ) CRLF)
70 * that's why we can always assume two consecutive line
71 * endings (we allow CR, LF, or CRLF, as some clients
72 * or servers might not use a full CRLF) to mark the end
73 * of the headers. The worst thing that would happen
74 * otherwise would be the packet not being desegmented
75 * or being interpreted as only headers.
77 * RFC 2326 says RTSP works the same way; RFC 3261 says SIP
82 * If header desegmentation is activated, check that all
83 * headers are in this tvbuff (search for an empty line
84 * marking end of headers) or request one more byte (we
85 * don't know how many bytes we'll need, so we just ask
88 if (desegment_headers && pinfo->can_desegment) {
91 next_offset_sav = next_offset;
93 length_remaining = tvb_length_remaining(tvb,
95 reported_length_remaining =
96 tvb_reported_length_remaining(tvb, next_offset);
99 * Request one more byte if there're no
100 * bytes left in the reported data (if there're
101 * bytes left in the reported data, but not in
102 * the available data, requesting more bytes
103 * won't help, as those bytes weren't captured).
105 if (reported_length_remaining < 1) {
106 pinfo->desegment_offset = offset;
107 pinfo->desegment_len = 1;
112 * Request one more byte if we cannot find a
113 * header (i.e. a line end).
115 linelen = tvb_find_line_end(tvb, next_offset,
116 -1, &next_offset, TRUE);
118 length_remaining >= reported_length_remaining) {
120 * Not enough data; ask for one more
123 pinfo->desegment_offset = offset;
124 pinfo->desegment_len = 1;
126 } else if (linelen == 0) {
128 * We found the end of the headers.
134 * Is this a Content-Length header?
135 * If not, it either means that we are in
136 * a different header line, or that we are
137 * at the end of the headers, or that there
138 * isn't enough data; the two latter cases
139 * have already been handled above.
141 if (desegment_body) {
143 * Check if we've found Content-Length.
145 if (tvb_strncaseeql(tvb, next_offset_sav,
146 "Content-Length:", 15) == 0) {
149 next_offset_sav + 15,
151 "%li", &content_length)
153 content_length_found = TRUE;
160 * The above loop ends when we reached the end of the headers, so
161 * there should be content_length byte after the 4 terminating bytes
162 * and next_offset points to after the end of the headers.
164 if (desegment_body && content_length_found) {
165 /* next_offset has been set because content-length was found */
166 if (!tvb_bytes_exist(tvb, next_offset, content_length)) {
167 length_remaining = tvb_length_remaining(tvb,
169 reported_length_remaining =
170 tvb_reported_length_remaining(tvb, next_offset);
171 if (length_remaining < reported_length_remaining) {
173 * It's a waste of time asking for more
174 * data, because that data wasn't captured.
178 if (length_remaining == -1)
179 length_remaining = 0;
180 pinfo->desegment_offset = offset;
181 pinfo->desegment_len =
182 content_length - length_remaining;
188 * No further desegmentation needed.