1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89
|
/*
* $Id: path.c,v 1.3 2006/01/30 16:37:30 agranig Exp $
*
* Helper functions for Path support.
*
* Copyright (C) 2006 Andreas Granig <agranig@linguin.org>
*
* This file is part of openser, a free SIP server.
*
* openser is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version
*
* openser is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*
*/
#include "../../data_lump.h"
#include "../../mem/mem.h"
#include "path.h"
#define ROUTE_STR "Route: "
#define ROUTE_LEN (sizeof(ROUTE_STR)-1)
/*
* Save given Path body as Route header in message.
*
* If another Route HF is found, it's placed right before that.
* Otherwise, it's placed after the last Via HF. If also no
* Via HF is found, it's placed as first HF.
*/
int insert_path_as_route(struct sip_msg* msg, str* path)
{
struct lump *anchor;
char *route;
struct hdr_field *hf, *last_via=0;
for (hf = msg->headers; hf; hf = hf->next) {
if (hf->type == HDR_ROUTE_T) {
break;
} else if (hf->type == HDR_VIA_T) {
last_via = hf;
}
}
if (hf) {
/* Route HF found, insert before it */
anchor = anchor_lump(msg, hf->name.s - msg->buf, 0, 0);
} else if(last_via) {
if (last_via->next) {
/* Via HF in between, insert after it */
anchor = anchor_lump(msg, last_via->next->name.s - msg->buf, 0, 0);
} else {
/* Via HF is last, so append */
anchor = anchor_lump(msg, msg->unparsed - msg->buf, 0, 0);
}
} else {
/* None of the above, insert as first */
anchor = anchor_lump(msg, msg->headers->name.s - msg->buf, 0, 0);
}
if (anchor == 0) {
LOG(L_ERR, "ERROR: insert_path_as_route(): Failed to get anchor\n");
return -1;
}
route = pkg_malloc(ROUTE_LEN + path->len + CRLF_LEN);
if (!route) {
LOG(L_ERR, "ERROR: insert_path_as_route(): Out of memory\n");
return -1;
}
memcpy(route, ROUTE_STR, ROUTE_LEN);
memcpy(route + ROUTE_LEN, path->s, path->len);
memcpy(route + ROUTE_LEN + path->len, CRLF, CRLF_LEN);
if (insert_new_lump_before(anchor, route, ROUTE_LEN + path->len + CRLF_LEN, 0) == 0) {
LOG(L_ERR, "ERROR: insert_path_as_route(): Failed to insert lump\n");
return -1;
}
return 0;
}
|