Ejemplo n.º 1
0
static int inherit_from_default_head(ds_db_head_t *head)
{
	unsigned int i;

	if (head == &default_db_head)
		return 0;

	for (i = 0; i < partition_param_count; ++i) {
		str *def_param = partition_params[i].getter_func(&default_db_head);
		str *p_param = partition_params[i].getter_func(head);

		if (p_param->len == 0 && def_param->len > 0) {
			/* Paramater not specified for function */
			if (strstr(partition_params[i].name.s, "avp")
				&& def_param->len > 0) {

				char *avp_end = q_memrchr(def_param->s, ')', def_param->len);
				if (avp_end == NULL) {
					LM_ERR ("wrong avp name %.*s\n", def_param->len,
							def_param->s);
					return -1;
				}

				p_param->len = def_param->len + 1 + head->partition_name.len;
				p_param->s = pkg_malloc(p_param->len);
				if (p_param->s == NULL) {
					LM_ERR ("no more private memory\n");
					return -1;
				}

				int fix_len = avp_end - def_param->s;
				int rem_len = def_param->len - fix_len;
				memcpy(p_param->s, def_param->s, fix_len);
				p_param->s[fix_len] = '_';
				memcpy(p_param->s + fix_len + 1, head->partition_name.s,
						head->partition_name.len);
				memcpy(p_param->s + fix_len + 1 + head->partition_name.len,
						def_param->s + fix_len, rem_len);
			}
			else
				memcpy(p_param, def_param, sizeof(str));
		}
	}
	return 0;
}
Ejemplo n.º 2
0
/*
 * Create a request
 */
char* build_uac_req(str* method, str* headers, str* body, dlg_t* dialog,
		int branch, struct cell *t, int* len, struct dest_info* dst)
{
	char* buf, *w, *p;
	str content_length, cseq, via;
	unsigned int maxfwd_len;
	int tbracket, fbracket;
	str fromtag = STR_NULL;
	str loc_tag = STR_NULL;

	if (!method || !dialog) {
		LM_ERR("invalid parameter value\n");
		return 0;
	}

	if (dialog->id.loc_tag.len<=0) {
		/* From Tag is mandatory in RFC3261 - generate one if not provided */
		generate_fromtag(&fromtag, &dialog->id.call_id);
		loc_tag = dialog->id.loc_tag;
		dialog->id.loc_tag = fromtag;
	}
	if (print_content_length(&content_length, body) < 0) {
		LM_ERR("error while printing content-length\n");
		return 0;
	}
	if (print_cseq_num(&cseq, dialog) < 0) {
		LM_ERR("error while printing CSeq number\n");
		return 0;
	}

	if(headers==NULL || headers->len<15
			|| _strnstr(headers->s, "Max-Forwards:", headers->len)==NULL) {
		maxfwd_len = MAXFWD_HEADER_LEN;
	} else {
		maxfwd_len = 0;
	}

	*len = method->len + 1 + dialog->hooks.request_uri->len + 1
		+ SIP_VERSION_LEN + CRLF_LEN;

	if (assemble_via(&via, t, dst, branch) < 0) {
		LM_ERR("error while assembling Via\n");
		return 0;
	}
	*len += via.len;

	if((p=q_memrchr(dialog->rem_uri.s, '>', dialog->rem_uri.len))!=NULL) {
		if((p==dialog->rem_uri.s + dialog->rem_uri.len - 1)
				|| *(p+1)==';') {
			tbracket = 0;
		} else {
			tbracket = 1;
		}
	} else {
		tbracket = 1;
	}
	if((p=q_memrchr(dialog->loc_uri.s, '>', dialog->loc_uri.len))!=NULL) {
		if((p==dialog->loc_uri.s + dialog->loc_uri.len - 1)
				|| *(p+1)==';') {
			fbracket = 0;
		} else {
			fbracket = 1;
		}
	} else {
		fbracket = 1;
	}

	*len += TO_LEN + dialog->rem_uri.len
		+ (dialog->id.rem_tag.len ? (TOTAG_LEN + dialog->id.rem_tag.len) : 0)
		+ CRLF_LEN;    /* To */
	if(tbracket) *len += 2; /* To-URI < > */
	*len += FROM_LEN + dialog->loc_uri.len
		+ (dialog->id.loc_tag.len ? (FROMTAG_LEN + dialog->id.loc_tag.len) : 0)
		+ CRLF_LEN;  /* From */
	if(fbracket) *len += 2; /* From-URI < > */
	*len += CALLID_LEN + dialog->id.call_id.len + CRLF_LEN;   /* Call-ID */
	*len += CSEQ_LEN + cseq.len + 1 + method->len + CRLF_LEN; /* CSeq */
	*len += calculate_routeset_length(dialog);                /* Route set */
	*len += maxfwd_len;                                       /* Max-forwards */
	*len += CONTENT_LENGTH_LEN + content_length.len
											+ CRLF_LEN; /* Content-Length */
	*len += ((server_signature && user_agent_hdr.len>0)
						? (user_agent_hdr.len + CRLF_LEN) : 0);	/* Signature */
	if(headers && headers->len>2) {
		/* Additional headers */
		*len += headers->len;
		/* End of header if missing */
		if(headers->s[headers->len - 1] != '\n')
			*len += CRLF_LEN;
	}
	*len += (body ? body->len : 0);                         /* Message body */
	*len += CRLF_LEN;                                       /* End of Header */

	buf = shm_malloc(*len + 1);
	if (!buf) {
		LM_ERR("no more shared memory (%d)\n", *len);
		goto error;
	}

	w = buf;

	w = print_request_uri(w, method, dialog, t, branch);  /* Request-URI */
	memapp(w, via.s, via.len);                            /* Top-most Via */
	w = print_to(w, dialog, t, tbracket);                 /* To */
	w = print_from(w, dialog, t, fbracket);               /* From */
	if(fromtag.len>0) {
		dialog->id.loc_tag = loc_tag;
	}
	w = print_cseq(w, &cseq, method, t);                  /* CSeq */
	w = print_callid(w, dialog, t);                       /* Call-ID */
	w = print_routeset(w, dialog);                        /* Route set */

	if(maxfwd_len>0)
		memapp(w, MAXFWD_HEADER, MAXFWD_HEADER_LEN);      /* Max-forwards */

	/* Content-Length */
	memapp(w, CONTENT_LENGTH, CONTENT_LENGTH_LEN);
	memapp(w, content_length.s, content_length.len);
	memapp(w, CRLF, CRLF_LEN);

	/* Server signature */
	if (server_signature && user_agent_hdr.len>0) {
		memapp(w, user_agent_hdr.s, user_agent_hdr.len);
		memapp(w, CRLF, CRLF_LEN);
	}
	if(headers && headers->len>2) {
		memapp(w, headers->s, headers->len);
		if(headers->s[headers->len - 1] != '\n')
			memapp(w, CRLF, CRLF_LEN);
	}
	memapp(w, CRLF, CRLF_LEN);
	if (body) memapp(w, body->s, body->len);

#ifdef EXTRA_DEBUG
	assert(w-buf == *len);
#endif

	memapp(w, "\0", 1);

	pkg_free(via.s);
	return buf;

error:
	pkg_free(via.s);
	return 0;
}
Ejemplo n.º 3
0
Archivo: tm.c Proyecto: Deni90/opensips
inline static int w_t_new_request(struct sip_msg* msg, char *p_method,
			char *p_ruri, char *p_from, char *p_to, char *p_body, char *p_ctx)
{
#define CONTENT_TYPE_HDR      "Content-Type: "
#define CONTENT_TYPE_HDR_LEN  (sizeof(CONTENT_TYPE_HDR)-1)
	static dlg_t dlg;
	struct usr_avp **avp_list;
	str ruri;
	str method;
	str body;
	str headers;
	str s;
	int_str ctx;
	char *p;

	memset( &dlg, 0, sizeof(dlg_t));

	/* evaluate the parameters */

	/* method */
	if ( fixup_get_svalue(msg, (gparam_p)p_method, &method)<0 ) {
		LM_ERR("failed to extract METHOD param\n");
		return -1;
	}
	LM_DBG("setting METHOD to <%.*s>\n", method.len, method.s);

	/* ruri - next hop is the same as RURI */
	dlg.hooks.next_hop = dlg.hooks.request_uri = &ruri;
	if ( fixup_get_svalue(msg, (gparam_p)p_ruri, &ruri)<0 ) {
		LM_ERR("failed to extract RURI param\n");
		return -1;
	}
	LM_DBG("setting RURI to <%.*s>\n",
		dlg.hooks.next_hop->len, dlg.hooks.next_hop->s);

	/* FROM URI + display */
	if ( fixup_get_svalue(msg, (gparam_p)p_from, &s)<0 ) {
		LM_ERR("failed to extract FROM param\n");
		return -1;
	}
	if ( (p=q_memrchr(s.s, ' ', s.len))==NULL ) {
		/* no display, only FROM URI */
		dlg.loc_uri = s;
		dlg.loc_dname.s = NULL;
		dlg.loc_dname.len = 0;
	} else {
		/* display + URI */
		dlg.loc_uri.s = p+1;
		dlg.loc_uri.len = s.s+s.len - dlg.loc_uri.s;
		dlg.loc_dname.s = s.s;
		dlg.loc_dname.len = p - s.s;
	}
	LM_DBG("setting FROM to <%.*s> + <%.*s>\n",
		dlg.loc_dname.len, dlg.loc_dname.s,
		dlg.loc_uri.len, dlg.loc_uri.s);

	/* TO URI + display */
	if ( fixup_get_svalue(msg, (gparam_p)p_to, &s)<0 ) {
		LM_ERR("failed to extract TO param\n");
		return -1;
	}
	if ( (p=q_memrchr(s.s, ' ', s.len))==NULL ) {
		/* no display, only TO URI */
		dlg.rem_uri = s;
		dlg.rem_dname.s = NULL;
		dlg.rem_dname.len = 0;
	} else {
		/* display + URI */
		dlg.rem_uri.s = p+1;
		dlg.rem_uri.len = s.s+s.len - dlg.rem_uri.s;
		dlg.rem_dname.s = s.s;
		dlg.rem_dname.len = p - s.s;
	}
	LM_DBG("setting TO to <%.*s> + <%.*s>\n",
		dlg.rem_dname.len, dlg.rem_dname.s,
		dlg.rem_uri.len, dlg.rem_uri.s);

	/* BODY and Content-Type */
	if (p_body!=NULL) {
		if ( fixup_get_svalue(msg, (gparam_p)p_body, &body)<0 ) {
			LM_ERR("failed to extract BODY param\n");
			return -1;
		}
		if ( (p=q_memchr(body.s, ' ', body.len))==NULL ) {
			LM_ERR("Content Type not found in the beginning of body <%.*s>\n",
				body.len, body.s);
			return -1;
		}
		/* build the Content-type header */
		headers.len = CONTENT_TYPE_HDR_LEN + (p-body.s) + CRLF_LEN;
		if ( (headers.s=(char*)pkg_malloc(headers.len))==NULL ) {
			LM_ERR("failed to get pkg mem (needed %d)\n",headers.len);
			return -1;
		}
		memcpy( headers.s, CONTENT_TYPE_HDR, CONTENT_TYPE_HDR_LEN);
		memcpy( headers.s+CONTENT_TYPE_HDR_LEN, body.s, p-body.s);
		memcpy( headers.s+CONTENT_TYPE_HDR_LEN+(p-body.s), CRLF, CRLF_LEN);
		/* set the body */
		body.len = body.s + body.len - (p+1);
		body.s = p + 1;
		LM_DBG("setting BODY to <%.*s> <%.*s>\n",
			headers.len, headers.s,
			body.len, body.s );
	} else {
		body.s = NULL;
		body.len = 0;
		headers.s = NULL;
		headers.len = 0;
	}

	/* context value */
	if (p_ctx!=NULL) {
		if ( fixup_get_svalue(msg, (gparam_p)p_ctx, &ctx.s)<0 ) {
			LM_ERR("failed to extract BODY param\n");
			if (p_body) pkg_free(headers.s);
			return -1;
		}
		LM_DBG("setting CTX AVP to <%.*s>\n", ctx.s.len, ctx.s.s);
		avp_list = set_avp_list( &dlg.avps );
		if (!add_avp( AVP_VAL_STR, uac_ctx_avp_id, ctx))
			LM_ERR("failed to add ctx AVP, ignorring...\n");
		set_avp_list( avp_list );
	}

	/* add cseq */
	dlg.loc_seq.value = DEFAULT_CSEQ;
	dlg.loc_seq.is_set = 1;

	/* add callid */
	generate_callid(&dlg.id.call_id);

	/* add FROM tag */
	generate_fromtag(&dlg.id.loc_tag, &dlg.id.call_id);
	/* TO tag is empty as this is a initial request */
	dlg.id.rem_tag.s = NULL;
	dlg.id.rem_tag.len = 0;

	/* do the actual sending now */
	if ( t_uac( &method, headers.s?&headers:NULL, body.s?&body:NULL,
	&dlg, 0, 0, 0) <= 0 ) {
		LM_ERR("failed to send the request out\n");
		if (headers.s) pkg_free(headers.s);
		if (dlg.avps) destroy_avp_list(&dlg.avps);
		return -1;
	}

	/* success -> do cleanup */
	if (headers.s) pkg_free(headers.s);
	return 1;
}