2 The oSIP library implements the Session Initiation Protocol (SIP -rfc3261-)
3 Copyright (C) 2001,2002,2003 Aymeric MOIZARD jack@atosc.org
5 This library is free software; you can redistribute it and/or
6 modify it under the terms of the GNU Lesser General Public
7 License as published by the Free Software Foundation; either
8 version 2.1 of the License, or (at your option) any later version.
10 This library is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 Lesser General Public License for more details.
15 You should have received a copy of the GNU Lesser General Public
16 License along with this library; if not, write to the Free Software
17 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
21 #include <osipparser2/osip_port.h>
22 #include <osipparser2/osip_parser.h>
27 static __osip_message_config_t pconfig[NUMBER_OF_HEADERS];
30 list of compact header:
33 e: Content-Encoding => ok
34 l: Content-Length => ok
37 s: Subject => NOT A SUPPORTED HEADER! will be
38 available in the list of unknown headers
42 /* This method must be called before using the parser */
47 pconfig[0].hname = ACCEPT;
48 pconfig[0].setheader = (&osip_message_set_accept);
49 pconfig[1].hname = ACCEPT_ENCODING;
50 pconfig[1].setheader = (&osip_message_set_accept_encoding);
51 pconfig[2].hname = ACCEPT_LANGUAGE;
52 pconfig[2].setheader = (&osip_message_set_accept_language);
53 pconfig[3].hname = ALERT_INFO;
54 pconfig[3].setheader = (&osip_message_set_alert_info);
55 pconfig[4].hname = ALLOW;
56 pconfig[4].setheader = (&osip_message_set_allow);
57 pconfig[5].hname = AUTHORIZATION;
58 pconfig[5].setheader = (&osip_message_set_authorization);
59 pconfig[6].hname = CONTENT_TYPE_SHORT; /* "l" */
60 pconfig[6].setheader = (&osip_message_set_content_type);
61 pconfig[7].hname = CALL_ID;
62 pconfig[7].setheader = (&osip_message_set_call_id);
63 pconfig[8].hname = CALL_INFO;
64 pconfig[8].setheader = (&osip_message_set_call_info);
65 pconfig[9].hname = CONTACT;
66 pconfig[9].setheader = (&osip_message_set_contact);
67 pconfig[10].hname = CONTENT_ENCODING;
68 pconfig[10].setheader = (&osip_message_set_content_encoding);
69 pconfig[11].hname = CONTENT_LENGTH;
70 pconfig[11].setheader = (&osip_message_set_content_length);
71 pconfig[12].hname = CONTENT_TYPE;
72 pconfig[12].setheader = (&osip_message_set_content_type);
73 pconfig[13].hname = CSEQ;
74 pconfig[13].setheader = (&osip_message_set_cseq);
75 pconfig[14].hname = CONTENT_ENCODING_SHORT; /* "e" */
76 pconfig[14].setheader = (&osip_message_set_content_encoding);
77 pconfig[15].hname = ERROR_INFO;
78 pconfig[15].setheader = (&osip_message_set_error_info);
79 pconfig[16].hname = FROM_SHORT; /* "f" */
80 pconfig[16].setheader = (&osip_message_set_from);
81 pconfig[17].hname = FROM;
82 pconfig[17].setheader = (&osip_message_set_from);
83 pconfig[18].hname = CALL_ID_SHORT; /* "i" */
84 pconfig[18].setheader = (&osip_message_set_call_id);
85 pconfig[19].hname = CONTENT_LENGTH_SHORT; /* "l" */
86 pconfig[19].setheader = (&osip_message_set_content_length);
87 pconfig[20].hname = CONTACT_SHORT; /* "m" */
88 pconfig[20].setheader = (&osip_message_set_contact);
89 pconfig[21].hname = MIME_VERSION;
90 pconfig[21].setheader = (&osip_message_set_mime_version);
91 pconfig[22].hname = PROXY_AUTHENTICATE;
92 pconfig[22].setheader = (&osip_message_set_proxy_authenticate);
93 pconfig[23].hname = PROXY_AUTHORIZATION;
94 pconfig[23].setheader = (&osip_message_set_proxy_authorization);
95 pconfig[24].hname = RECORD_ROUTE;
96 pconfig[24].setheader = (&osip_message_set_record_route);
97 pconfig[25].hname = ROUTE;
98 pconfig[25].setheader = (&osip_message_set_route);
99 pconfig[26].hname = TO_SHORT;
100 pconfig[26].setheader = (&osip_message_set_to);
101 pconfig[27].hname = TO;
102 pconfig[27].setheader = (&osip_message_set_to);
103 pconfig[28].hname = VIA_SHORT;
104 pconfig[28].setheader = (&osip_message_set_via);
105 pconfig[29].hname = VIA;
106 pconfig[29].setheader = (&osip_message_set_via);
107 pconfig[30].hname = WWW_AUTHENTICATE;
108 pconfig[30].setheader = (&osip_message_set_www_authenticate);
113 /* search the header hname through pconfig[] tab.
114 A quicker algorithm should be used.
115 It returns the index of the header in the __osip_message_config_t tab.
118 __osip_message_is_known_header (const char *hname)
122 int isup = NUMBER_OF_HEADERS;
123 int i = NUMBER_OF_HEADERS / 2;
125 length = strlen (hname);
129 if (i < 0 || i > NUMBER_OF_HEADERS - 1)
132 if ((length == strlen (pconfig[i].hname))
133 && osip_strncasecmp (hname, (const char *) pconfig[i].hname,
138 return -1; /* not found */
139 if (iinf == isup - 1)
141 if ((i < NUMBER_OF_HEADERS - 1)
142 && (length == strlen (pconfig[i + 1].hname))
143 && osip_strncasecmp (hname,
144 (const char *) pconfig[i + 1].hname,
149 /* Unreachable code??
150 if ((i > 0) && (length == strlen (pconfig[i - 1].hname))
151 && osip_strncasecmp (hname,
152 (const char *) pconfig[i - 1].hname, length) == 0)
158 if (0 < osip_strncasecmp (hname,
159 (const char *) pconfig[i].hname, length))
161 /* if this is true, search further */
163 if (i == i + (isup - i) / 2)
166 i = i + (isup - i) / 2;
171 if (i == i - (i - iinf) / 2)
174 i = i - (i - iinf) / 2;
176 } /* end of (while (1)) */
180 #else /* USE_GPERF */
181 /* C code produced by gperf version 2.7.2 */
182 /* Command-line: gperf sip.gperf */
184 #define TOTAL_KEYWORDS 53
185 #define MIN_WORD_LENGTH 1
186 #define MAX_WORD_LENGTH 19
187 #define MIN_HASH_VALUE 1
188 #define MAX_HASH_VALUE 132
189 /* maximum key range = 132, duplicates = 0 */
198 static unsigned char asso_values[] = {
199 133, 133, 133, 133, 133, 133, 133, 133, 133, 133,
200 133, 133, 133, 133, 133, 133, 133, 133, 133, 133,
201 133, 133, 133, 133, 133, 133, 133, 133, 133, 133,
202 133, 133, 133, 133, 133, 133, 133, 133, 133, 133,
203 133, 133, 133, 133, 133, 133, 133, 133, 133, 133,
204 133, 133, 133, 133, 133, 133, 133, 133, 133, 133,
205 133, 133, 133, 133, 133, 133, 133, 133, 133, 133,
206 133, 133, 133, 133, 133, 133, 133, 133, 133, 133,
207 133, 133, 133, 133, 133, 133, 133, 133, 133, 133,
208 133, 133, 133, 133, 133, 133, 133, 20, 133, 25,
209 41, 0, 5, 20, 25, 1, 133, 133, 10, 60,
210 60, 0, 0, 0, 45, 15, 45, 30, 40, 0,
211 133, 15, 133, 133, 133, 133, 133, 133, 133, 133,
212 133, 133, 133, 133, 133, 133, 133, 133, 133, 133,
213 133, 133, 133, 133, 133, 133, 133, 133, 133, 133,
214 133, 133, 133, 133, 133, 133, 133, 133, 133, 133,
215 133, 133, 133, 133, 133, 133, 133, 133, 133, 133,
216 133, 133, 133, 133, 133, 133, 133, 133, 133, 133,
217 133, 133, 133, 133, 133, 133, 133, 133, 133, 133,
218 133, 133, 133, 133, 133, 133, 133, 133, 133, 133,
219 133, 133, 133, 133, 133, 133, 133, 133, 133, 133,
220 133, 133, 133, 133, 133, 133, 133, 133, 133, 133,
221 133, 133, 133, 133, 133, 133, 133, 133, 133, 133,
222 133, 133, 133, 133, 133, 133, 133, 133, 133, 133,
223 133, 133, 133, 133, 133, 133, 133, 133, 133, 133,
224 133, 133, 133, 133, 133, 133
226 static const __osip_message_config_t pconfig[133] = {
228 {CONTENT_ENCODING_SHORT, &osip_message_set_content_encoding},
230 {CALL_ID_SHORT, &osip_message_set_call_id},
231 {"", NULL}, {"", NULL}, {"", NULL}, {"", NULL}, {"", NULL}, {"", NULL},
232 {ERROR_INFO, &osip_message_set_error_info},
233 {FROM_SHORT, &osip_message_set_from},
235 {PROXY_REQUIRE, NULL},
236 {"", NULL}, {"", NULL},
237 {WWW_AUTHENTICATE, &osip_message_set_www_authenticate},
239 {PROXY_AUTHENTICATE, &osip_message_set_proxy_authenticate},
240 {"", NULL}, {"", NULL},
241 {CONTENT_LENGTH_SHORT, &osip_message_set_content_length},
245 {ALLOW, &osip_message_set_allow},
249 {CSEQ, &osip_message_set_cseq},
250 {ALERT_INFO, &osip_message_set_alert_info},
251 {SUBJECT_SHORT, NULL},
252 {"", NULL}, {"", NULL},
253 {CALL_INFO, &osip_message_set_call_info},
254 {ACCEPT_LANGUAGE, &osip_message_set_accept_language},
256 {CONTENT_TYPE, &osip_message_set_content_type},
258 {AUTHENTICATION_INFO, NULL},
260 {CONTENT_LANGUAGE, NULL},
261 {"", NULL}, {"", NULL}, {"", NULL},
264 {"to", &osip_message_set_to},
265 {"", NULL}, {"", NULL},
266 {ROUTE, &osip_message_set_route},
267 {CONTENT_TYPE_SHORT, &osip_message_set_content_type},
271 {ACCEPT_ENCODING, &osip_message_set_accept_encoding},
273 {RECORD_ROUTE, &osip_message_set_record_route},
274 {"", NULL}, {"", NULL}, {"", NULL},
275 {CONTENT_ENCODING, &osip_message_set_content_encoding},
277 {VIA, &osip_message_set_via},
278 {CONTENT_LENGTH, &osip_message_set_content_length},
283 {FROM, &osip_message_set_from},
285 {ACCEPT, &osip_message_set_accept},
286 {ORGANIZATION, NULL},
287 {CALL_ID, &osip_message_set_call_id},
288 {"", NULL}, {"", NULL}, {"", NULL},
289 {CONTACT, &osip_message_set_contact},
291 {PROXY_AUTHORIZATION, &osip_message_set_proxy_authorization},
293 {VIA_SHORT, &osip_message_set_via},
295 {"", NULL}, {"", NULL},
298 {MAX_FORWARDS, NULL},
299 {"", NULL}, {"", NULL}, {"", NULL},
300 {TO_SHORT, &osip_message_set_to},
302 {AUTHORIZATION, &osip_message_set_authorization},
303 {"", NULL}, {"", NULL}, {"", NULL}, {"", NULL}, {"", NULL}, {"", NULL}, {"",
306 {"", NULL}, {"", NULL},
307 {CONTENT_DISPOSITION, NULL},
308 {"", NULL}, {"", NULL}, {"", NULL}, {"", NULL}, {"", NULL}, {"", NULL}, {"",
310 {"", NULL}, {"", NULL},
311 {"", NULL}, {"", NULL}, {"", NULL}, {"", NULL}, {"", NULL}, {"", NULL}, {"",
313 {CONTACT_SHORT, &osip_message_set_contact},
314 {"", NULL}, {"", NULL}, {"", NULL}, {"", NULL}, {"", NULL}, {"", NULL}, {"",
316 {"", NULL}, {"", NULL},
318 {MIME_VERSION, &osip_message_set_mime_version}
322 register const char *str;
323 register unsigned int len;
325 return len + asso_values[(unsigned char) str[len - 1]] +
326 asso_values[(unsigned char) str[0]];
333 in_word_set (str, len)
334 register const char *str;
335 register unsigned int len;
337 if (len <= MAX_WORD_LENGTH && len >= MIN_WORD_LENGTH)
339 register int key = hash (str, len);
341 if (key <= MAX_HASH_VALUE && key >= 0)
343 register const char *s = pconfig[key].hname;
345 if (*str == *s && !strcmp (str + 1, s + 1)
346 && (pconfig[key].setheader != NULL))
356 return 0; /* do not need initialization when using gperf */
360 __osip_message_is_known_header (const char *hname)
364 iLength = strlen (hname);
365 return in_word_set (hname, iLength);
370 /* This method calls the method that is able to parse the header */
372 __osip_message_call_method (int i, osip_message_t * dest, const char *hvalue)
374 return pconfig[i].setheader (dest, hvalue);