/* generate a template sdp */ sdp_message_t * sdp_context_generate_template (sdp_context_t * ctx) { sdp_message_t *local; int inet6; sdp_message_init (&local); if (strchr(ctx->localip,':')!=NULL){ inet6=1; }else inet6=0; if (!inet6){ sdp_message_v_version_set (local, osip_strdup ("0")); sdp_message_o_origin_set (local, osip_strdup (ctx->username), osip_strdup ("123456"), osip_strdup ("654321"), osip_strdup ("IN"), osip_strdup ("IP4"), osip_strdup (ctx->localip)); sdp_message_s_name_set (local, osip_strdup ("A conversation")); sdp_message_c_connection_add (local, -1, osip_strdup ("IN"), osip_strdup ("IP4"), osip_strdup (ctx->localip), NULL, NULL); sdp_message_t_time_descr_add (local, osip_strdup ("0"), osip_strdup ("0")); }else{ sdp_message_v_version_set (local, osip_strdup ("0")); sdp_message_o_origin_set (local, osip_strdup (ctx->username), osip_strdup ("123456"), osip_strdup ("654321"), osip_strdup ("IN"), osip_strdup ("IP6"), osip_strdup (ctx->localip)); sdp_message_s_name_set (local, osip_strdup ("A conversation")); sdp_message_c_connection_add (local, -1, osip_strdup ("IN"), osip_strdup ("IP6"), osip_strdup (ctx->localip), NULL, NULL); sdp_message_t_time_descr_add (local, osip_strdup ("0"), osip_strdup ("0")); } return local; }
static int sdp_partial_clone (osip_negotiation_t * config, osip_negotiation_ctx_t * con, sdp_message_t * remote, sdp_message_t ** dest) { int i; sdp_message_v_version_set (*dest, osip_strdup ("0")); /* those fields MUST be set */ sdp_message_o_origin_set (*dest, osip_strdup (config->o_username), osip_strdup (config->o_session_id), osip_strdup (config->o_session_version), osip_strdup (config->o_nettype), osip_strdup (config->o_addrtype), osip_strdup (config->o_addr)); sdp_message_s_name_set (*dest, osip_strdup (remote->s_name)); if (config->fcn_set_info != NULL) config->fcn_set_info (con, *dest); if (config->fcn_set_uri != NULL) config->fcn_set_uri (con, *dest); if (config->fcn_set_emails != NULL) config->fcn_set_emails (con, *dest); if (config->fcn_set_phones != NULL) config->fcn_set_phones (con, *dest); if (config->c_nettype != NULL) sdp_message_c_connection_add (*dest, -1, osip_strdup (config->c_nettype), osip_strdup (config->c_addrtype), osip_strdup (config->c_addr), osip_strdup (config->c_addr_multicast_ttl), osip_strdup (config->c_addr_multicast_int)); { /* offer-answer draft says we must copy the "t=" line */ char *tmp = sdp_message_t_start_time_get (remote, 0); char *tmp2 = sdp_message_t_stop_time_get (remote, 0); if (tmp == NULL || tmp2 == NULL) return -1; /* no t line?? */ i = sdp_message_t_time_descr_add (*dest, osip_strdup (tmp), osip_strdup (tmp2)); if (i != 0) return -1; } if (config->fcn_set_attributes != NULL) config->fcn_set_attributes (con, *dest, -1); return 0; }
static sdp_message_t *create_generic_sdp(const SalMediaDescription *desc) { sdp_message_t *local; int inet6; char sessid[16]; char sessver[16]; snprintf(sessid,16,"%i",desc->session_id); snprintf(sessver,16,"%i",desc->session_ver); sdp_message_init (&local); if (strchr(desc->addr,':')!=NULL){ inet6=1; }else inet6=0; sdp_message_v_version_set (local, osip_strdup ("0")); sdp_message_o_origin_set (local, osip_strdup (desc->username), osip_strdup (sessid), osip_strdup (sessver), osip_strdup ("IN"), inet6 ? osip_strdup("IP6") : osip_strdup ("IP4"), osip_strdup (desc->addr)); sdp_message_s_name_set (local, osip_strdup ("Talk")); if(!sal_media_description_has_dir (desc,SalStreamSendOnly)) { sdp_message_c_connection_add (local, -1, osip_strdup ("IN"), inet6 ? osip_strdup ("IP6") : osip_strdup ("IP4"), osip_strdup (desc->addr), NULL, NULL); } else { sdp_message_c_connection_add (local, -1, osip_strdup ("IN"), inet6 ? osip_strdup ("IP6") : osip_strdup ("IP4"), inet6 ? osip_strdup ("::0") : osip_strdup ("0.0.0.0"), NULL, NULL); } sdp_message_t_time_descr_add (local, osip_strdup ("0"), osip_strdup ("0")); if (desc->bandwidth>0) sdp_message_b_bandwidth_add (local, -1, osip_strdup ("AS"), int_2char(desc->bandwidth)); return local; }
static void add_line(sdp_message_t *msg, int lineno, const SalStreamDescription *desc){ const char *mt=NULL; const MSList *elem; const char *addr; const char *dir="sendrecv"; int port; bool_t strip_well_known_rtpmaps; switch (desc->type) { case SalAudio: mt="audio"; break; case SalVideo: mt="video"; break; case SalOther: mt=desc->typeother; break; } if (desc->candidates[0].addr[0]!='\0'){ addr=desc->candidates[0].addr; port=desc->candidates[0].port; }else{ addr=desc->addr; port=desc->port; } /*only add a c= line within the stream description if address are differents*/ if (strcmp(addr,sdp_message_c_addr_get(msg, -1, 0))!=0){ bool_t inet6; if (strchr(addr,':')!=NULL){ inet6=TRUE; }else inet6=FALSE; sdp_message_c_connection_add (msg, lineno, osip_strdup ("IN"), inet6 ? osip_strdup ("IP6") : osip_strdup ("IP4"), osip_strdup (addr), NULL, NULL); } sdp_message_m_media_add (msg, osip_strdup (mt), int_2char (port), NULL, osip_strdup ("RTP/AVP")); if (desc->bandwidth>0) sdp_message_b_bandwidth_add (msg, lineno, osip_strdup ("AS"), int_2char(desc->bandwidth)); if (desc->ptime>0) sdp_message_a_attribute_add(msg,lineno,osip_strdup("ptime"), int_2char(desc->ptime)); strip_well_known_rtpmaps=ms_list_size(desc->payloads)>5; if (desc->payloads){ for(elem=desc->payloads;elem!=NULL;elem=elem->next){ add_payload(msg, lineno, (PayloadType*)elem->data,strip_well_known_rtpmaps); } }else{ /* to comply with SDP we cannot have an empty payload type number list */ /* as it happens only when mline is declined with a zero port, it does not matter to put whatever codec*/ sdp_message_m_payload_add (msg,lineno, int_2char (0)); } switch(desc->dir){ case SalStreamSendRecv: /*dir="sendrecv";*/ dir=NULL; break; case SalStreamRecvOnly: dir="recvonly"; break; case SalStreamSendOnly: dir="sendonly"; break; case SalStreamInactive: dir="inactive"; break; } if (dir) sdp_message_a_attribute_add (msg, lineno, osip_strdup (dir),NULL); }
int osip_negotiation_sdp_build_offer (osip_negotiation_t * config, osip_negotiation_ctx_t * con, sdp_message_t ** sdp, char *audio_port, char *video_port) { int i; int media_line = 0; i = sdp_message_init (sdp); if (i != 0) return -1; sdp_message_v_version_set (*sdp, osip_strdup ("0")); /* those fields MUST be set */ sdp_message_o_origin_set (*sdp, osip_strdup (config->o_username), osip_strdup (config->o_session_id), osip_strdup (config->o_session_version), osip_strdup (config->o_nettype), osip_strdup (config->o_addrtype), osip_strdup (config->o_addr)); sdp_message_s_name_set (*sdp, osip_strdup ("A call")); if (config->fcn_set_info != NULL) config->fcn_set_info (con, *sdp); if (config->fcn_set_uri != NULL) config->fcn_set_uri (con, *sdp); if (config->fcn_set_emails != NULL) config->fcn_set_emails (con, *sdp); if (config->fcn_set_phones != NULL) config->fcn_set_phones (con, *sdp); if (config->c_nettype != NULL) sdp_message_c_connection_add (*sdp, -1, osip_strdup (config->c_nettype), osip_strdup (config->c_addrtype), osip_strdup (config->c_addr), osip_strdup (config->c_addr_multicast_ttl), osip_strdup (config->c_addr_multicast_int)); { /* offer-answer draft says we must copy the "t=" line */ /*BEGIN 3082101267 00201037 20130823 modified*/ int now = osip_time (NULL); /*END 3082101267 00201037 20130823 modified*/ char *tmp = osip_malloc (15); char *tmp2 = osip_malloc (15); sprintf (tmp, "%i", now); sprintf (tmp2, "%i", now + 3600); i = sdp_message_t_time_descr_add (*sdp, tmp, tmp2); if (i != 0) return -1; } if (config->fcn_set_attributes != NULL) config->fcn_set_attributes (con, *sdp, -1); /* add all audio codec */ if (!osip_list_eol (config->audio_codec, 0)) { int pos = 0; __payload_t *my = (__payload_t *) osip_list_get (config->audio_codec, pos); /* all media MUST have the same PROTO, PORT. */ sdp_message_m_media_add (*sdp, osip_strdup ("audio"), osip_strdup (audio_port), osip_strdup (my->number_of_port), osip_strdup (my->proto)); while (!osip_list_eol (config->audio_codec, pos)) { my = (__payload_t *) osip_list_get (config->audio_codec, pos); sdp_message_m_payload_add (*sdp, media_line, osip_strdup (my->payload)); if (my->a_rtpmap != NULL) sdp_message_a_attribute_add (*sdp, media_line, osip_strdup ("rtpmap"), osip_strdup (my->a_rtpmap)); pos++; } media_line++; } /* add all video codec */ if (!osip_list_eol (config->video_codec, 0)) { int pos = 0; __payload_t *my = (__payload_t *) osip_list_get (config->video_codec, pos); /* all media MUST have the same PROTO, PORT. */ sdp_message_m_media_add (*sdp, osip_strdup ("video"), osip_strdup (video_port), osip_strdup (my->number_of_port), osip_strdup (my->proto)); while (!osip_list_eol (config->video_codec, pos)) { my = (__payload_t *) osip_list_get (config->video_codec, pos); sdp_message_m_payload_add (*sdp, media_line, osip_strdup (my->payload)); if (my->a_rtpmap != NULL) sdp_message_a_attribute_add (*sdp, media_line, osip_strdup ("rtpmap"), osip_strdup (my->a_rtpmap)); pos++; } media_line++; } return 0; }
static int sdp_confirm_media (osip_negotiation_t * config, osip_negotiation_ctx_t * context, sdp_message_t * remote, sdp_message_t ** dest) { char *payload; char *tmp, *tmp2, *tmp3, *tmp4; int ret; int i; int k; int audio_qty = 0; /* accepted audio line: do not accept more than one */ int video_qty = 0; i = 0; while (!sdp_message_endof_media (remote, i)) { tmp = sdp_message_m_media_get (remote, i); tmp2 = sdp_message_m_port_get (remote, i); tmp3 = sdp_message_m_number_of_port_get (remote, i); tmp4 = sdp_message_m_proto_get (remote, i); if (tmp == NULL) return -1; sdp_message_m_media_add (*dest, osip_strdup (tmp), osip_strdup ("0"), NULL, osip_strdup (tmp4)); k = 0; if (0 == strncmp (tmp, "audio", 5)) { do { payload = sdp_message_m_payload_get (remote, i, k); if (payload != NULL) { __payload_t *my_payload = osip_negotiation_find_audio_payload (config, payload); if (my_payload != NULL) /* payload is supported */ { ret = -1; /* somtimes, codec can be refused even if supported */ if (config->fcn_accept_audio_codec != NULL) ret = config->fcn_accept_audio_codec (context, tmp2, tmp3, audio_qty, payload); if (0 == ret) { sdp_message_m_payload_add (*dest, i, osip_strdup (payload)); if (my_payload->a_rtpmap != NULL) sdp_message_a_attribute_add (*dest, i, osip_strdup ("rtpmap"), osip_strdup (my_payload-> a_rtpmap)); if (my_payload->c_nettype != NULL) { sdp_media_t *med = osip_list_get ((*dest)->m_medias, i); if (osip_list_eol (med->c_connections, 0)) sdp_message_c_connection_add (*dest, i, osip_strdup (my_payload-> c_nettype), osip_strdup (my_payload-> c_addrtype), osip_strdup (my_payload-> c_addr), osip_strdup (my_payload-> c_addr_multicast_ttl), osip_strdup (my_payload-> c_addr_multicast_int)); } } } } k++; } while (payload != NULL); if (NULL != sdp_message_m_payload_get (*dest, i, 0)) audio_qty = 1; } else if (0 == strncmp (tmp, "video", 5)) { do { payload = sdp_message_m_payload_get (remote, i, k); if (payload != NULL) { __payload_t *my_payload = osip_negotiation_find_video_payload (config, payload); if (my_payload != NULL) /* payload is supported */ { ret = -1; if (config->fcn_accept_video_codec != NULL) ret = config->fcn_accept_video_codec (context, tmp2, tmp3, video_qty, payload); if (0 == ret) { sdp_message_m_payload_add (*dest, i, osip_strdup (payload)); /* TODO set the attribute list (rtpmap..) */ if (my_payload->a_rtpmap != NULL) sdp_message_a_attribute_add (*dest, i, osip_strdup ("rtpmap"), osip_strdup (my_payload-> a_rtpmap)); if (my_payload->c_nettype != NULL) { sdp_media_t *med = osip_list_get ((*dest)->m_medias, i); if (osip_list_eol (med->c_connections, 0)) sdp_message_c_connection_add (*dest, i, osip_strdup (my_payload-> c_nettype), osip_strdup (my_payload-> c_addrtype), osip_strdup (my_payload-> c_addr), osip_strdup (my_payload-> c_addr_multicast_ttl), osip_strdup (my_payload-> c_addr_multicast_int)); } } } } k++; } while (payload != NULL); if (NULL != sdp_message_m_payload_get (*dest, i, 0)) video_qty = 1; } else { do { payload = sdp_message_m_payload_get (remote, i, k); if (payload != NULL) { __payload_t *my_payload = osip_negotiation_find_other_payload (config, payload); if (my_payload != NULL) /* payload is supported */ { ret = -1; if (config->fcn_accept_other_codec != NULL) ret = config->fcn_accept_other_codec (context, tmp, tmp2, tmp3, payload); if (0 == ret) { sdp_message_m_payload_add (*dest, i, osip_strdup (payload)); /* rtpmap has no meaning here! */ if (my_payload->c_nettype != NULL) { sdp_media_t *med = osip_list_get ((*dest)->m_medias, i); if (osip_list_eol (med->c_connections, 0)) sdp_message_c_connection_add (*dest, i, osip_strdup (my_payload-> c_nettype), osip_strdup (my_payload-> c_addrtype), osip_strdup (my_payload-> c_addr), osip_strdup (my_payload-> c_addr_multicast_ttl), osip_strdup (my_payload-> c_addr_multicast_int)); } } } } k++; } while (payload != NULL); } i++; } return 0; }