- use SIGUSR2 for dmalloc debugging (SIGUSR1 is occupied

with old libc5 & threads)
- reworked calling parameters for passing SIP data
This commit is contained in:
Thomas Ries
2004-06-13 12:46:33 +00:00
parent fd687df2f7
commit 200f6ea926
9 changed files with 244 additions and 183 deletions
+4
View File
@@ -1,5 +1,9 @@
0.5.7
=====
13-Jun-2004: - fix: get_ip_by_host() and buffers for reentrant functions
12-Jun-2004: - use SIGUSR2 for dmalloc debugging (SIGUSR1 is occupied
with old libc5 & threads)
- reworked calling parameters for passing SIP data
11-Jun-2004: - silenced some MSN Messenger provoked WARNings
29-May-2004: - "determine next hop" also takes Route header into account
(outgoing packets only, incoming can not have a proxy
+4 -4
View File
@@ -55,7 +55,7 @@ static char *auth_getpwd(char *username);
* STS_FAILURE : authentication failed
* STS_NEEDAUTH: authentication needed
*/
int authenticate_proxy(osip_message_t *request) {
int authenticate_proxy(sip_ticket_t *ticket) {
osip_proxy_authorization_t *proxy_auth=NULL;
/* required by config? */
@@ -64,7 +64,7 @@ int authenticate_proxy(osip_message_t *request) {
}
/* supplied by UA? */
osip_message_get_proxy_authorization(request, 0, &proxy_auth);
osip_message_get_proxy_authorization(ticket->sipmsg, 0, &proxy_auth);
if (proxy_auth == NULL) {
DEBUGC(DBCLASS_AUTH,"proxy-auth required, not supplied by UA");
return STS_NEED_AUTH;
@@ -88,7 +88,7 @@ int authenticate_proxy(osip_message_t *request) {
* STS_SUCCESS
* STS_FAILURE
*/
int auth_include_authrq(osip_message_t *response) {
int auth_include_authrq(sip_ticket_t *ticket) {
osip_proxy_authenticate_t *p_auth;
char *realm=NULL;
@@ -109,7 +109,7 @@ int auth_include_authrq(osip_message_t *response) {
return STS_FAILURE;
}
osip_list_add (response->proxy_authenticates, p_auth, -1);
osip_list_add (ticket->sipmsg->proxy_authenticates, p_auth, -1);
DEBUGC(DBCLASS_AUTH,"added authentication header");
+34 -13
View File
@@ -74,7 +74,7 @@ extern struct lcl_if_s local_addresses;
* 10. Forward the new request
* 11. Set timer C
*/
int proxy_request (osip_message_t *request, struct sockaddr_in *from) {
int proxy_request (sip_ticket_t *ticket) {
int i;
int sts;
int type;
@@ -82,12 +82,21 @@ int proxy_request (osip_message_t *request, struct sockaddr_in *from) {
osip_uri_t *url;
int port;
char *buffer;
osip_message_t *request;
struct sockaddr_in *from;
#define REQTYP_INCOMING 1
#define REQTYP_OUTGOING 2
DEBUGC(DBCLASS_PROXY,"proxy_request");
if (ticket==NULL) {
ERROR("proxy_request: called with NULL ticket");
return STS_FAILURE;
}
request=ticket->sipmsg;
from=&ticket->from;
/*
* RFC 3261, Section 16.4
@@ -336,7 +345,7 @@ int proxy_request (osip_message_t *request, struct sockaddr_in *from) {
/* careful - an internal UA might send an request to another internal UA.
This would be caught here, so don't do this. This situation should be
caught in the default part of the CASE statement below */
if (is_sipuri_local(request) == STS_TRUE) {
if (is_sipuri_local(ticket) == STS_TRUE) {
WARN("unsupported request [%s] directed to proxy from %s@%s -> %s@%s",
request->sip_method? request->sip_method:"*NULL*",
request->from->url->username? request->from->url->username:"*NULL*",
@@ -344,14 +353,14 @@ int proxy_request (osip_message_t *request, struct sockaddr_in *from) {
url->username? url->username : "*NULL*",
url->host? url->host : "*NULL*");
sip_gen_response(request, 403 /*forbidden*/);
sip_gen_response(ticket, 403 /*forbidden*/);
return STS_FAILURE;
}
#endif
/* rewrite Contact header to represent the masqued address */
sip_rewrite_contact(request, DIR_OUTGOING);
sip_rewrite_contact(ticket, DIR_OUTGOING);
/* if an INVITE, rewrite body */
if (MSG_IS_INVITE(request)) {
@@ -388,7 +397,7 @@ int proxy_request (osip_message_t *request, struct sockaddr_in *from) {
* How about "408 Request Timeout" ?
*
*/
sip_gen_response(request, 408 /* Request Timeout */);
sip_gen_response(ticket, 408 /* Request Timeout */);
return STS_FAILURE;
}
@@ -613,12 +622,12 @@ We should use the first Route header to send the packet to
*/
/* add my Via header line (outbound interface)*/
if (type == REQTYP_INCOMING) {
sts = sip_add_myvia(request, IF_INBOUND);
sts = sip_add_myvia(ticket, IF_INBOUND);
if (sts == STS_FAILURE) {
ERROR("adding my inbound via failed!");
}
} else {
sts = sip_add_myvia(request, IF_OUTBOUND);
sts = sip_add_myvia(ticket, IF_OUTBOUND);
if (sts == STS_FAILURE) {
ERROR("adding my outbound via failed!");
return STS_FAILURE;
@@ -640,7 +649,8 @@ We should use the first Route header to send the packet to
return STS_FAILURE;
}
sipsock_send(sendto_addr, port, buffer, strlen(buffer));
sipsock_send(sendto_addr, port, ticket->protocol,
buffer, strlen(buffer));
osip_free (buffer);
/*
@@ -660,7 +670,7 @@ We should use the first Route header to send the packet to
* STS_SUCCESS on success
* STS_FAILURE on error
*/
int proxy_response (osip_message_t *response, struct sockaddr_in *from) {
int proxy_response (sip_ticket_t *ticket) {
int i;
int sts;
int type;
@@ -668,18 +678,28 @@ int proxy_response (osip_message_t *response, struct sockaddr_in *from) {
osip_via_t *via;
int port;
char *buffer;
osip_message_t *response;
struct sockaddr_in *from;
#define RESTYP_INCOMING 1
#define RESTYP_OUTGOING 2
DEBUGC(DBCLASS_PROXY,"proxy_response");
if (ticket==NULL) {
ERROR("proxy_response: called with NULL ticket");
return STS_FAILURE;
}
response=ticket->sipmsg;
from=&ticket->from;
/*
* RFC 3261, Section 16.11
* Proxy Behavior - Remove my Via header field value
*/
/* remove my Via header line */
sts = sip_del_myvia(response);
sts = sip_del_myvia(ticket);
if (sts == STS_FAILURE) {
DEBUGC(DBCLASS_PROXY,"not addressed to my VIA, ignoring response");
return STS_FAILURE;
@@ -794,7 +814,7 @@ int proxy_response (osip_message_t *response, struct sockaddr_in *from) {
* Rewrite Contact header back to represent the true address.
* Other responses do return the Contact header of the sender.
*/
sip_rewrite_contact(response, DIR_INCOMING);
sip_rewrite_contact(ticket, DIR_INCOMING);
}
/*
@@ -840,7 +860,7 @@ int proxy_response (osip_message_t *response, struct sockaddr_in *from) {
response->from->url->host : "*NULL*");
/* rewrite Contact header to represent the masqued address */
sip_rewrite_contact(response, DIR_OUTGOING);
sip_rewrite_contact(ticket, DIR_OUTGOING);
/* If an 200 OK or 183 Trying answer to an INVITE request,
* rewrite body */
@@ -905,7 +925,8 @@ int proxy_response (osip_message_t *response, struct sockaddr_in *from) {
return STS_FAILURE;
}
sipsock_send(sendto_addr, port, buffer, strlen(buffer));
sipsock_send(sendto_addr, port, ticket->protocol,
buffer, strlen(buffer));
osip_free (buffer);
return STS_SUCCESS;
}
+29 -24
View File
@@ -163,7 +163,7 @@ void register_shut(void) {
* STS_FAILURE : registration failed
* STS_NEED_AUTH : authentication needed
*/
int register_client(osip_message_t *my_msg, int force_lcl_masq) {
int register_client(sip_ticket_t *ticket, int force_lcl_masq) {
int i, j, n, sts;
int expires;
time_t time_now;
@@ -181,17 +181,19 @@ int register_client(osip_message_t *my_msg, int force_lcl_masq) {
* RFC 3261, Section 16.3 step 6
* Proxy Behavior - Request Validation - Proxy-Authorization
*/
sts = authenticate_proxy(my_msg);
sts = authenticate_proxy(ticket);
if (sts == STS_FAILURE) {
/* failed */
WARN("proxy authentication failed for %s@%s",
(my_msg->to->url->username)? my_msg->to->url->username : "*NULL*",
my_msg->to->url->host);
(ticket->sipmsg->to->url->username)?
ticket->sipmsg->to->url->username : "*NULL*",
ticket->sipmsg->to->url->host);
return STS_FAILURE;
} else if (sts == STS_NEED_AUTH) {
/* needed */
DEBUGC(DBCLASS_REG,"proxy authentication needed for %s@%s",
my_msg->to->url->username,my_msg->to->url->host);
ticket->sipmsg->to->url->username,
ticket->sipmsg->to->url->host);
return STS_NEED_AUTH;
}
}
@@ -215,14 +217,14 @@ int register_client(osip_message_t *my_msg, int force_lcl_masq) {
DEBUGC(DBCLASS_BABBLE,"sip_register:");
/* evaluate Expires Header field */
osip_message_get_expires(my_msg, 0, &expires_hdr);
osip_message_get_expires(ticket->sipmsg, 0, &expires_hdr);
/*
* look for an Contact expires parameter - in case of REGISTER
* these two are equal. The Contact expires has higher priority!
*/
osip_contact_param_get_byname(
(osip_contact_t*) my_msg->contacts->node->element,
(osip_contact_t*) ticket->sipmsg->contacts->node->element,
EXPIRES, &expires_param);
if (expires_param && expires_param->gvalue) {
@@ -235,10 +237,10 @@ int register_client(osip_message_t *my_msg, int force_lcl_masq) {
/* it seems, the expires field is not present everywhere... */
DEBUGC(DBCLASS_REG,"no 'expires' header found - set time to 600 sec");
expires=600;
osip_message_set_expires(my_msg, "600");
osip_message_set_expires(ticket->sipmsg, "600");
}
url1_to=my_msg->to->url;
url1_to=ticket->sipmsg->to->url;
@@ -257,7 +259,8 @@ int register_client(osip_message_t *my_msg, int force_lcl_masq) {
* (gdb) p *((osip_contact_t*)(sip->contacts->node->element))
* $5 = {displayname = 0x8af8848 "*", url = 0x0, gen_params = 0x8af8838}
*/
url1_contact=((osip_contact_t*)(my_msg->contacts->node->element))->url;
url1_contact=((osip_contact_t*)
(ticket->sipmsg->contacts->node->element))->url;
if ((url1_contact == NULL) || (url1_contact->host == NULL)) {
/* Don't have reqiured Contact fields */
ERROR("tried registration with empty Contact header");
@@ -310,10 +313,11 @@ int register_client(osip_message_t *my_msg, int force_lcl_masq) {
/* write entry */
urlmap[i].active=1;
/* Contact: field */
osip_uri_clone( ((osip_contact_t*)(my_msg->contacts->node->element))->url,
&urlmap[i].true_url);
osip_uri_clone( ((osip_contact_t*)
(ticket->sipmsg->contacts->node->element))->url,
&urlmap[i].true_url);
/* To: field */
osip_uri_clone( my_msg->to->url,
osip_uri_clone( ticket->sipmsg->to->url,
&urlmap[i].reg_url);
DEBUGC(DBCLASS_REG,"create new entry for %s@%s <-> %s@%s at slot=%i",
@@ -326,7 +330,7 @@ int register_client(osip_message_t *my_msg, int force_lcl_masq) {
/*
* try to figure out if we ought to do some masquerading
*/
osip_uri_clone( my_msg->to->url,
osip_uri_clone( ticket->sipmsg->to->url,
&urlmap[i].masq_url);
n=configuration.mask_host.used;
@@ -338,9 +342,9 @@ int register_client(osip_message_t *my_msg, int force_lcl_masq) {
DEBUG("%i entries in MASK config table", n);
for (j=0; j<n; j++) {
DEBUG("compare [%s] <-> [%s]",configuration.mask_host.string[j],
my_msg->to->url->host);
ticket->sipmsg->to->url->host);
if (strcmp(configuration.mask_host.string[j],
my_msg->to->url->host)==0)
ticket->sipmsg->to->url->host)==0)
break;
}
if (j<n) {
@@ -382,11 +386,12 @@ int register_client(osip_message_t *my_msg, int force_lcl_masq) {
*/
/* Contact: field */
osip_uri_free(urlmap[i].true_url);
osip_uri_clone( ((osip_contact_t*)(my_msg->contacts->node->element))->url,
&urlmap[i].true_url);
osip_uri_clone( ((osip_contact_t*)
(ticket->sipmsg->contacts->node->element))->url,
&urlmap[i].true_url);
/* To: field */
osip_uri_free(urlmap[i].reg_url);
osip_uri_clone( my_msg->to->url,
osip_uri_clone( ticket->sipmsg->to->url,
&urlmap[i].reg_url);
}
/* give some safety margin for the next update */
@@ -459,7 +464,7 @@ void register_agemap(void) {
* STS_SUCCESS on success
* STS_FAILURE on error
*/
int register_response(osip_message_t *request, int flag) {
int register_response(sip_ticket_t *ticket, int flag) {
osip_message_t *response;
int code;
int sts;
@@ -486,13 +491,13 @@ int register_response(osip_message_t *request, int flag) {
}
/* create the response template */
if ((response=msg_make_template_reply(request, code))==NULL) {
if ((response=msg_make_template_reply(ticket, code))==NULL) {
ERROR("register_response: error in msg_make_template_reply");
return STS_FAILURE;
}
/* insert the expiration header */
osip_message_get_expires(request, 0, &expires_hdr);
osip_message_get_expires(ticket->sipmsg, 0, &expires_hdr);
if (expires_hdr) {
osip_message_set_expires(response, expires_hdr->hvalue);
}
@@ -500,7 +505,7 @@ int register_response(osip_message_t *request, int flag) {
/* if we send back an proxy authentication needed,
include the Proxy-Authenticate field */
if (code == 407) {
auth_include_authrq(response);
auth_include_authrq(ticket);
}
/* get the IP address from existing VIA header */
@@ -534,7 +539,7 @@ int register_response(osip_message_t *request, int flag) {
port=configuration.sip_listen_port;
}
sipsock_send(addr, port, buffer, strlen(buffer));
sipsock_send(addr, port, ticket->protocol, buffer, strlen(buffer));
/* free the resources */
osip_message_free(response);
+2 -2
View File
@@ -110,8 +110,8 @@ int security_check_raw(char *sip_buffer, int size) {
* STS_SUCCESS if ok
* STS_FAILURE if the packed did not pass the checks
*/
int security_check_sip(osip_message_t *sip){
int security_check_sip(sip_ticket_t *ticket){
osip_message_t *sip=ticket->sipmsg;
if (MSG_IS_REQUEST(sip)) {
/* check for existing SIP URI in request */
if ((sip->req_uri == NULL) || (sip->req_uri->scheme == NULL)) {
+22 -17
View File
@@ -59,7 +59,8 @@ extern struct urlmap_s urlmap[]; /* URL mapping table */
*
* RETURNS a pointer to osip_message_t
*/
osip_message_t *msg_make_template_reply (osip_message_t * request, int code) {
osip_message_t *msg_make_template_reply (sip_ticket_t *ticket, int code) {
osip_message_t *request=ticket->sipmsg;
osip_message_t *response;
int pos;
@@ -114,7 +115,7 @@ osip_message_t *msg_make_template_reply (osip_message_t * request, int code) {
* STS_TRUE if loop detected
* STS_FALSE if no loop
*/
int check_vialoop (osip_message_t *my_msg) {
int check_vialoop (sip_ticket_t *ticket) {
/*
!!! actually this is a problematic one.
1) for requests, I must search the whole VIA list
@@ -134,6 +135,7 @@ int check_vialoop (osip_message_t *my_msg) {
to-be-unique ID)
*/
osip_message_t *my_msg=ticket->sipmsg;
int sts;
int pos;
int found_own_via;
@@ -383,7 +385,8 @@ mismatch:
* STS_TRUE if the request is addressed local
* STS_FALSE otherwise
*/
int is_sipuri_local (osip_message_t *sip) {
int is_sipuri_local (sip_ticket_t *ticket) {
osip_message_t *sip=ticket->sipmsg;
int sts, found;
struct in_addr addr_uri, addr_myself;
char *my_interfaces[]=
@@ -520,7 +523,7 @@ int check_rewrite_rq_uri (osip_message_t *sip) {
* STS_SUCCESS on success
* STS_FAILURE on error
*/
int sip_gen_response(osip_message_t *request, int code) {
int sip_gen_response(sip_ticket_t *ticket, int code) {
osip_message_t *response;
int sts;
osip_via_t *via;
@@ -529,8 +532,8 @@ int sip_gen_response(osip_message_t *request, int code) {
struct in_addr addr;
/* create the response template */
if ((response=msg_make_template_reply(request, code))==NULL) {
ERROR("proxy_response: error in msg_make_template_reply");
if ((response=msg_make_template_reply(ticket, code))==NULL) {
ERROR("sip_gen_response: error in msg_make_template_reply");
return STS_FAILURE;
}
@@ -538,7 +541,7 @@ int sip_gen_response(osip_message_t *request, int code) {
osip_message_get_via (response, 0, &via);
if (via == NULL)
{
ERROR("proxy_response: Cannot send response - no via field");
ERROR("sip_gen_response: Cannot send response - no via field");
return STS_FAILURE;
}
@@ -558,7 +561,7 @@ int sip_gen_response(osip_message_t *request, int code) {
sts = osip_message_to_str(response, &buffer);
if (sts != 0) {
ERROR("proxy_response: msg_2char failed");
ERROR("sip_gen_response: msg_2char failed");
return STS_FAILURE;
}
@@ -570,7 +573,7 @@ int sip_gen_response(osip_message_t *request, int code) {
}
/* send to destination */
sipsock_send(addr, port, buffer, strlen(buffer));
sipsock_send(addr, port, ticket->protocol, buffer, strlen(buffer));
/* free the resources */
osip_message_free(response);
@@ -588,7 +591,7 @@ int sip_gen_response(osip_message_t *request, int code) {
* STS_SUCCESS on success
* STS_FAILURE on error
*/
int sip_add_myvia (osip_message_t *request, int interface) {
int sip_add_myvia (sip_ticket_t *ticket, int interface) {
struct in_addr addr;
char tmp[URL_STRING_SIZE];
osip_via_t *via;
@@ -611,7 +614,7 @@ int sip_add_myvia (osip_message_t *request, int interface) {
}
}
sts = sip_calculate_branch_id(request, branch_id);
sts = sip_calculate_branch_id(ticket, branch_id);
sprintf(tmp, "SIP/2.0/UDP %s:%i;branch=%s;", utils_inet_ntoa(addr),
configuration.sip_listen_port, branch_id);
@@ -623,7 +626,7 @@ int sip_add_myvia (osip_message_t *request, int interface) {
sts = osip_via_parse(via, tmp);
if (sts!=0) return STS_FAILURE;
osip_list_add(request->vias,via,0);
osip_list_add(ticket->sipmsg->vias,via,0);
return STS_SUCCESS;
}
@@ -636,12 +639,12 @@ int sip_add_myvia (osip_message_t *request, int interface) {
* STS_SUCCESS on success
* STS_FAILURE on error
*/
int sip_del_myvia (osip_message_t *response) {
int sip_del_myvia (sip_ticket_t *ticket) {
osip_via_t *via;
int sts;
DEBUGC(DBCLASS_PROXY,"deleting topmost VIA");
via = osip_list_get (response->vias, 0);
via = osip_list_get (ticket->sipmsg->vias, 0);
if ( via == NULL ) {
ERROR("Got empty VIA list - is your UA configured properly?");
@@ -653,7 +656,7 @@ int sip_del_myvia (osip_message_t *response) {
return STS_FAILURE;
}
sts = osip_list_remove(response->vias, 0);
sts = osip_list_remove(ticket->sipmsg->vias, 0);
osip_via_free (via);
return STS_SUCCESS;
}
@@ -668,7 +671,8 @@ int sip_del_myvia (osip_message_t *response) {
* STS_SUCCESS on success
* STS_FAILURE on error
*/
int sip_rewrite_contact (osip_message_t *sip_msg, int direction) {
int sip_rewrite_contact (sip_ticket_t *ticket, int direction) {
osip_message_t *sip_msg=ticket->sipmsg;
osip_contact_t *contact;
int i;
@@ -733,7 +737,7 @@ int sip_rewrite_contact (osip_message_t *sip_msg, int direction) {
* STS_SUCCESS on success
* STS_FAILURE on error
*/
int sip_calculate_branch_id (osip_message_t *sip_msg, char *id) {
int sip_calculate_branch_id (sip_ticket_t *ticket, char *id) {
/* RFC3261 section 16.11 recommends the following procedure:
* The stateless proxy MAY use any technique it likes to guarantee
* uniqueness of its branch IDs across transactions. However, the
@@ -754,6 +758,7 @@ int sip_calculate_branch_id (osip_message_t *sip_msg, char *id) {
* - 1st part (unique calculated ID
* - 2nd part (value for loop detection) <<- not yet used by siproxd
*/
osip_message_t *sip_msg=ticket->sipmsg;
static char *magic_cookie="z9hG4bK";
osip_via_t *via;
osip_uri_param_t *param=NULL;
+44 -41
View File
@@ -72,9 +72,8 @@ int main (int argc, char *argv[])
int sts;
int i;
int access;
struct sockaddr_in from;
char buff [BUFFER_SIZE];
osip_message_t *my_msg=NULL;
sip_ticket_t ticket;
extern char *optarg;
int ch1;
@@ -99,8 +98,8 @@ int main (int argc, char *argv[])
if (sigaction(SIGINT, &act, NULL)) {
ERROR("Failed to install SIGINT handler");
}
if (sigaction(SIGUSR1, &act, NULL)) {
ERROR("Failed to install SIGUSR1 handler");
if (sigaction(SIGUSR2, &act, NULL)) {
ERROR("Failed to install SIGUSR2 handler");
}
@@ -245,11 +244,11 @@ int main (int argc, char *argv[])
if (dmalloc_dump) {
dmalloc_dump=0;
#ifdef DMALLOC
INFO("SIGUSR1 - DMALLOC statistics is dumped");
INFO("SIGUSR2 - DMALLOC statistics is dumped");
dmalloc_log_stats();
dmalloc_log_unfreed();
#else
INFO("SIGUSR1 - DMALLOC support is not compiled in");
INFO("SIGUSR2 - DMALLOC support is not compiled in");
#endif
}
@@ -259,11 +258,11 @@ int main (int argc, char *argv[])
/* got input, process */
DEBUGC(DBCLASS_BABBLE,"back from sip_wait");
i=sipsock_read(&buff, sizeof(buff)-1, &from);
i=sipsock_read(&buff, sizeof(buff)-1, &ticket.from, &ticket.protocol);
buff[i]='\0';
/* evaluate the access lists (IP based filter)*/
access=accesslist_check(from);
access=accesslist_check(ticket.from);
if (access == 0) continue; /* there are no resources to free */
/* integrity checks */
@@ -271,8 +270,8 @@ int main (int argc, char *argv[])
if (sts != STS_SUCCESS) continue; /* there are no resources to free */
/* init sip_msg */
sts=osip_message_init(&my_msg);
my_msg->message=NULL;
sts=osip_message_init(&ticket.sipmsg);
ticket.sipmsg->message=NULL;
if (sts != 0) {
ERROR("osip_message_init() failed... this is not good");
continue; /* skip, there are no resources to free */
@@ -283,7 +282,7 @@ int main (int argc, char *argv[])
* Proxy Behavior - Request Validation - Reasonable Syntax
* (parse the received message)
*/
sts=osip_message_parse(my_msg, buff);
sts=osip_message_parse(ticket.sipmsg, buff);
if (sts != 0) {
ERROR("osip_message_parse() failed... this is not good");
DUMP_BUFFER(-1, buff, i);
@@ -291,7 +290,7 @@ int main (int argc, char *argv[])
}
/* integrity checks - parsed buffer*/
sts=security_check_sip(my_msg);
sts=security_check_sip(&ticket);
if (sts != STS_SUCCESS) {
ERROR("security_check_sip() failed... this is not good");
DUMP_BUFFER(-1, buff, i);
@@ -314,7 +313,7 @@ int main (int argc, char *argv[])
osip_header_t *max_forwards;
int forwards_count = DEFAULT_MAXFWD;
osip_message_get_max_forwards(my_msg, 0, &max_forwards);
osip_message_get_max_forwards(ticket.sipmsg, 0, &max_forwards);
if (max_forwards && max_forwards->hvalue) {
forwards_count = atoi(max_forwards->hvalue);
}
@@ -322,7 +321,7 @@ int main (int argc, char *argv[])
DEBUGC(DBCLASS_PROXY,"checking Max-Forwards (=%i)",forwards_count);
if (forwards_count <= 0) {
DEBUGC(DBCLASS_SIP, "Forward count reached 0 -> 483 response");
sip_gen_response(my_msg, 483 /*Too many hops*/);
sip_gen_response(&ticket, 483 /*Too many hops*/);
goto end_loop; /* skip and free resources */
}
@@ -333,14 +332,15 @@ int main (int argc, char *argv[])
* Proxy Behavior - Request Validation - Loop Detection check
* (check for loop and return 482 if a loop is detected)
*/
if (check_vialoop(my_msg) == STS_TRUE) {
if (check_vialoop(&ticket) == STS_TRUE) {
/* make sure we don't end up in endless loop when detecting
* an loop in an "loop detected" message - brrr */
if (MSG_IS_RESPONSE(my_msg) && MSG_TEST_CODE(my_msg, 482)) {
if (MSG_IS_RESPONSE(ticket.sipmsg) &&
MSG_TEST_CODE(ticket.sipmsg, 482)) {
DEBUGC(DBCLASS_SIP,"loop in loop-response detected, ignoring");
} else {
DEBUGC(DBCLASS_SIP,"via loop detected, ignoring request");
sip_gen_response(my_msg, 482 /*Loop detected*/);
sip_gen_response(&ticket, 482 /*Loop detected*/);
}
goto end_loop; /* skip and free resources */
}
@@ -359,10 +359,12 @@ int main (int argc, char *argv[])
/* NOT IMPLEMENTED */
DEBUGC(DBCLASS_SIP,"received SIP type %s:%s",
(MSG_IS_REQUEST(my_msg))? "REQ" : "RES",
(MSG_IS_REQUEST(my_msg) ?
((my_msg->sip_method)? my_msg->sip_method : "NULL") :
((my_msg->reason_phrase) ? my_msg->reason_phrase : "NULL")));
(MSG_IS_REQUEST(ticket.sipmsg))? "REQ" : "RES",
(MSG_IS_REQUEST(ticket.sipmsg) ?
((ticket.sipmsg->sip_method)?
ticket.sipmsg->sip_method : "NULL") :
((ticket.sipmsg->reason_phrase) ?
ticket.sipmsg->reason_phrase : "NULL")));
/*
* if an REQ REGISTER, check if it is directed to myself,
@@ -370,12 +372,13 @@ int main (int argc, char *argv[])
* - If I'm the registrar, register & generate answer
* - If I'm just the outbound proxy, register, rewrite & forward
*/
if (MSG_IS_REGISTER(my_msg) && MSG_IS_REQUEST(my_msg)) {
if (MSG_IS_REGISTER(ticket.sipmsg) &&
MSG_IS_REQUEST(ticket.sipmsg)) {
if (access & ACCESSCTL_REG) {
osip_uri_t *url;
struct in_addr addr1, addr2, addr3;
url = osip_message_get_uri(my_msg);
url = osip_message_get_uri(ticket.sipmsg);
sts = get_ip_by_host(url->host, &addr1);
get_ip_by_ifname(configuration.inbound_if,&addr2);
@@ -385,17 +388,17 @@ int main (int argc, char *argv[])
((memcmp(&addr1, &addr2, sizeof(addr1)) == 0) ||
(memcmp(&addr1, &addr3, sizeof(addr1)) == 0))) {
/* I'm the registrar, send response myself */
sts = register_client(my_msg, 0);
sts = register_response(my_msg, sts);
sts = register_client(&ticket, 0);
sts = register_response(&ticket, sts);
} else {
/* I'm just the outbound proxy */
DEBUGC(DBCLASS_SIP,"proxying REGISTER request to:%s",url->host);
sts = register_client(my_msg, 1);
sts = proxy_request(my_msg, &from);
sts = register_client(&ticket, 1);
sts = proxy_request(&ticket);
}
} else {
WARN("non-authorized registration attempt from %s",
utils_inet_ntoa(from.sin_addr));
utils_inet_ntoa(ticket.from.sin_addr));
}
/*
@@ -406,34 +409,34 @@ int main (int argc, char *argv[])
} else if (get_ip_by_ifname(configuration.outbound_if,NULL) !=
STS_SUCCESS) {
DEBUGC(DBCLASS_SIP, "got a %s to proxy, but outbound interface "
"is down", (MSG_IS_REQUEST(my_msg))? "REQ" : "RES");
"is down", (MSG_IS_REQUEST(ticket.sipmsg))? "REQ" : "RES");
if (MSG_IS_REQUEST(my_msg))
sip_gen_response(my_msg, 408 /*request timeout*/);
if (MSG_IS_REQUEST(ticket.sipmsg))
sip_gen_response(&ticket, 408 /*request timeout*/);
/*
* MSG is a request, add current via entry,
* do a lookup in the URLMAP table and
* send to the final destination
*/
} else if (MSG_IS_REQUEST(my_msg)) {
} else if (MSG_IS_REQUEST(ticket.sipmsg)) {
if (access & ACCESSCTL_SIP) {
sts = proxy_request(my_msg, &from);
sts = proxy_request(&ticket);
} else {
INFO("non-authorized request received from %s",
utils_inet_ntoa(from.sin_addr));
utils_inet_ntoa(ticket.from.sin_addr));
}
/*
* MSG is a response, remove current via and
* send to the next VIA in chain
*/
} else if (MSG_IS_RESPONSE(my_msg)) {
} else if (MSG_IS_RESPONSE(ticket.sipmsg)) {
if (access & ACCESSCTL_SIP) {
sts = proxy_response(my_msg, &from);
sts = proxy_response(&ticket);
} else {
INFO("non-authorized response received from %s",
utils_inet_ntoa(from.sin_addr));
utils_inet_ntoa(ticket.from.sin_addr));
}
/*
@@ -441,8 +444,8 @@ int main (int argc, char *argv[])
*/
} else {
ERROR("received unsupported SIP type %s %s",
(MSG_IS_REQUEST(my_msg))? "REQ" : "RES",
my_msg->sip_method);
(MSG_IS_REQUEST(ticket.sipmsg))? "REQ" : "RES",
ticket.sipmsg->sip_method);
}
@@ -450,7 +453,7 @@ int main (int argc, char *argv[])
* free the SIP message buffers
*/
end_loop:
osip_message_free(my_msg);
osip_message_free(ticket.sipmsg);
} /* while TRUE */
exit_prg:
@@ -482,6 +485,6 @@ int main (int argc, char *argv[])
static void sighandler(int sig) {
if (sig==SIGTERM) exit_program=1;
if (sig==SIGINT) exit_program=1;
if (sig==SIGUSR1) dmalloc_dump=1;
if (sig==SIGUSR2) dmalloc_dump=1;
return;
}
+96 -80
View File
@@ -25,86 +25,6 @@
#endif
/* function returns STS_* status values vvv */
/* sock.c */
int sipsock_listen (void); /*X*/
int sipsock_wait();
int sipsock_read(void *buf, size_t bufsize,
struct sockaddr_in *from);
int sipsock_send(struct in_addr addr, int port, /*X*/
char *buffer, int size);
int sockbind(struct in_addr ipaddr, int localport, int errflg);
/* register.c */
void register_init(void);
void register_shut(void);
int register_client(osip_message_t *request, int force_lcl_masq); /*X*/
void register_agemap(void);
int register_response(osip_message_t *request, int flag); /*X*/
/* proxy.c */
int proxy_request (osip_message_t *request, struct sockaddr_in *from); /*X*/
int proxy_response (osip_message_t *response, struct sockaddr_in *from);/*X*/
int proxy_rewrite_invitation_body(osip_message_t *m, int direction); /*X*/
int proxy_rewrite_request_uri(osip_message_t *mymsg, int idx); /*X*/
/* utils.c */
int get_ip_by_host(char *hostname, struct in_addr *addr); /*X*/
void secure_enviroment (void);
int get_ip_by_ifname(char *ifname, struct in_addr *retaddr); /*X*/
char *utils_inet_ntoa(struct in_addr in);
int utils_inet_aton(const char *cp, struct in_addr *inp);
/* sip_utils.c */
osip_message_t * msg_make_template_reply (osip_message_t * request, int code);
int check_vialoop (osip_message_t *my_msg); /*X*/
int is_via_local (osip_via_t *via); /*X*/
int compare_url(osip_uri_t *url1, osip_uri_t *url2); /*X*/
int compare_callid(osip_call_id_t *cid1, osip_call_id_t *cid2); /*X*/
int is_sipuri_local (osip_message_t *sip); /*X*/
int check_rewrite_rq_uri (osip_message_t *sip); /*X*/
int sip_gen_response(osip_message_t *request, int code); /*X*/
#define IF_OUTBOUND 0
#define IF_INBOUND 1
int sip_add_myvia (osip_message_t *request, int interface); /*X*/
int sip_del_myvia (osip_message_t *response); /*X*/
int sip_rewrite_contact (osip_message_t *sip_msg, int direction); /*X*/
int sip_calculate_branch_id (osip_message_t *sip_msg, char *id); /*X*/
/* readconf.c */
int read_config(char *name, int search); /*X*/
/* rtpproxy.c */
int rtpproxy_init( void ); /*X*/
int rtp_start_fwd (osip_call_id_t *callid, char *client_id, /*X*/
int direction, int media_stream_no,
struct in_addr outbound_ipaddr, int *outboundport,
struct in_addr lcl_client_ipaddr, int lcl_clientport);
int rtp_stop_fwd (osip_call_id_t *callid, int direction); /*X*/
void rtpproxy_kill( void ); /*X*/
/* accessctl.c */
int accesslist_check(struct sockaddr_in from);
/* security.c */
int security_check_raw(char *sip_buffer, int size); /*X*/
int security_check_sip(osip_message_t *sip); /*X*/
/* auth.c */
int authenticate_proxy(osip_message_t *request); /*X*/
int auth_include_authrq(osip_message_t *response); /*X*/
void CvtHex(char *hash, char *hashstring);
/* fwapi.h */
int fwapi_start_rtp(int rtp_direction,
struct in_addr local_ipaddr, int local_port,
struct in_addr remote_ipaddr, int remote_port);
int fwapi_stop_rtp(int rtp_direction,
struct in_addr local_ipaddr, int local_port,
struct in_addr remote_ipaddr, int remote_port);
/*
* table to hold the client registrations
*/
@@ -163,6 +83,102 @@ struct siproxd_config {
char *pid_file;
};
/*
* SIP ticket
*/
typedef struct {
osip_message_t *sipmsg; /* SIP */
struct sockaddr_in from; /* received from */
#define PROTO_UNKN -1
#define PROTO_UDP 1
#define PROTO_TCP 2
int protocol; /* received by protocol */
} sip_ticket_t;
/*
* Function prototypes
*/
/* function returns STS_* status values vvv */
/* sock.c */
int sipsock_listen (void); /*X*/
int sipsock_wait();
int sipsock_read(void *buf, size_t bufsize,
struct sockaddr_in *from, int *protocol);
int sipsock_send(struct in_addr addr, int port, int protocol, /*X*/
char *buffer, int size);
int sockbind(struct in_addr ipaddr, int localport, int errflg);
/* register.c */
void register_init(void);
void register_shut(void);
int register_client(sip_ticket_t *ticket, int force_lcl_masq); /*X*/
void register_agemap(void);
int register_response(sip_ticket_t *ticket, int flag); /*X*/
/* proxy.c */
int proxy_request (sip_ticket_t *ticket); /*X*/
int proxy_response (sip_ticket_t *ticket); /*X*/
int proxy_rewrite_invitation_body(osip_message_t *m, int direction); /*X*/
int proxy_rewrite_request_uri(osip_message_t *mymsg, int idx); /*X*/
/* utils.c */
int get_ip_by_host(char *hostname, struct in_addr *addr); /*X*/
void secure_enviroment (void);
int get_ip_by_ifname(char *ifname, struct in_addr *retaddr); /*X*/
char *utils_inet_ntoa(struct in_addr in);
int utils_inet_aton(const char *cp, struct in_addr *inp);
/* sip_utils.c */
osip_message_t * msg_make_template_reply (sip_ticket_t *ticket, int code);
int check_vialoop (sip_ticket_t *ticket); /*X*/
int is_via_local (osip_via_t *via); /*X*/
int compare_url(osip_uri_t *url1, osip_uri_t *url2); /*X*/
int compare_callid(osip_call_id_t *cid1, osip_call_id_t *cid2); /*X*/
int is_sipuri_local (sip_ticket_t *ticket); /*X*/
int check_rewrite_rq_uri (osip_message_t *sip); /*X*/
int sip_gen_response(sip_ticket_t *ticket, int code); /*X*/
#define IF_OUTBOUND 0
#define IF_INBOUND 1
int sip_add_myvia (sip_ticket_t *ticket, int interface); /*X*/
int sip_del_myvia (sip_ticket_t *ticket); /*X*/
int sip_rewrite_contact (sip_ticket_t *ticket, int direction); /*X*/
int sip_calculate_branch_id (sip_ticket_t *ticket, char *id); /*X*/
/* readconf.c */
int read_config(char *name, int search); /*X*/
/* rtpproxy.c */
int rtpproxy_init( void ); /*X*/
int rtp_start_fwd (osip_call_id_t *callid, char *client_id, /*X*/
int direction, int media_stream_no,
struct in_addr outbound_ipaddr, int *outboundport,
struct in_addr lcl_client_ipaddr, int lcl_clientport);
int rtp_stop_fwd (osip_call_id_t *callid, int direction); /*X*/
void rtpproxy_kill( void ); /*X*/
/* accessctl.c */
int accesslist_check(struct sockaddr_in from);
/* security.c */
int security_check_raw(char *sip_buffer, int size); /*X*/
int security_check_sip(sip_ticket_t *ticket); /*X*/
/* auth.c */
int authenticate_proxy(sip_ticket_t *ticket); /*X*/
int auth_include_authrq(sip_ticket_t *ticket); /*X*/
void CvtHex(char *hash, char *hashstring);
/* fwapi.c */
int fwapi_start_rtp(int rtp_direction,
struct in_addr local_ipaddr, int local_port,
struct in_addr remote_ipaddr, int remote_port);
int fwapi_stop_rtp(int rtp_direction,
struct in_addr local_ipaddr, int local_port,
struct in_addr remote_ipaddr, int remote_port);
/*
* some constant definitions
+9 -2
View File
@@ -107,16 +107,18 @@ int sipsock_wait(void) {
* from is modified to return the sockaddr_in of the sender
*/
int sipsock_read(void *buf, size_t bufsize,
struct sockaddr_in *from) {
struct sockaddr_in *from, int *protocol) {
int count;
socklen_t fromlen;
fromlen=sizeof(struct sockaddr_in);
*protocol = PROTO_UDP; /* up to now, unly UDP */
count=recvfrom(sip_udp_socket, buf, bufsize, 0,
(struct sockaddr *)from, &fromlen);
if (count<0) {
WARN("recvfrom() returned error [%s]",strerror(errno));
*protocol = PROTO_UNKN;
}
DEBUGC(DBCLASS_NET,"received UDP packet from %s, count=%i",
@@ -134,7 +136,7 @@ int sipsock_read(void *buf, size_t bufsize,
* STS_SUCCESS on success
* STS_FAILURE on error
*/
int sipsock_send(struct in_addr addr, int port,
int sipsock_send(struct in_addr addr, int port, int protocol,
char *buffer, int size) {
struct sockaddr_in dst_addr;
int sts;
@@ -150,6 +152,11 @@ int sipsock_send(struct in_addr addr, int port,
return STS_FAILURE;
}
if (protocol != PROTO_UDP) {
ERROR("sipsock_send: only UDP supported by now");
return STS_FAILURE;
}
dst_addr.sin_family = AF_INET;
memcpy(&dst_addr.sin_addr.s_addr, &addr, sizeof(struct in_addr));
dst_addr.sin_port= htons(port);