Main Page | Modules | Alphabetical List | Data Structures | File List | Data Fields | Globals | Examples

formatter.c

Go to the documentation of this file.
00001 /*
00002   This file is part of FreeSDP
00003   Copyright (C) 2001,2002,2003 Federico Montesino Pouzols <fedemp@altern.org>
00004   
00005   FreeSDP is free software; you can redistribute it and/or modify it
00006   under the terms of the GNU General Public License as published by
00007   the Free Software Foundation; either version 2 of the License, or
00008   (at your option) any later version.
00009 
00010   This program is distributed in the hope that it will be useful,
00011   but WITHOUT ANY WARRANTY; without even the implied warranty of
00012   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00013   GNU General Public License for more details.
00014 
00015   You should have received a copy of the GNU General Public License
00016   along with this program; if not, write to the Free Software
00017   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
00018 */
00019 
00026 #include "formatterpriv.h"
00027 
00028 const char *bandwidth_modifier_strings[] = {
00029   "", "", "CT", "AS", "RS", "RR" 
00030 };
00031 
00032 const char *network_type_strings[] = {
00033   "", "IN"
00034 };
00035 
00036 const char *address_type_strings[] = {
00037   "", "IP4", "IP6"
00038 };
00039 
00040 const char *bw_mod_type_strings[] = {
00041   "", "CT", "AS", "RS", "RR"
00042 };
00043 
00044 const char *encryption_method_strings[] = {
00045   "", "clear", "base64", "uri"
00046 };
00047 
00048 const char *sendrecv_mode_strings[] = {
00049   "", "sendrecv", "recvonly", "sendonly", "inactive"
00050 }; 
00051 
00052 const char *session_type_strings[] = {
00053   "", "broadcast", "meeting", "moderated", "test", "H332"
00054 };
00055 
00056 const char *media_strings[] ={
00057   "", "audio", "video", "text", "application", "data", "control"
00058 };
00059 
00060 const char *tp_strings[] = {
00061   "", "RTP/AVP", "udp", "TCP", "UDPTL", "vat", "rtp", "H.320"
00062 };
00063 
00064 const char *orient_strings[] = {
00065   "", "portrait", "landscape", "seascape"
00066 };
00067 
00068 fsdp_error_t
00069 fsdp_make_description(fsdp_description_t **dsc, 
00070                 unsigned int sdp_version,
00071                 const char *session_name, const char *session_id,
00072                 const char *announcement_version,
00073                 const char *owner_username,
00074                 fsdp_network_type_t owner_nt, 
00075                 fsdp_address_type_t owner_at,
00076                 const char *owner_address,
00077                 time_t start, time_t stop)
00078 {
00079   fsdp_description_t *obj; 
00080 
00081   if ( (NULL == dsc) || (NULL == session_name) || (NULL == session_id) ||
00082        (NULL == announcement_version) ||
00083        (NULL == owner_username) || (NULL == owner_address) )
00084     return FSDPE_INVALID_PARAMETER;
00085 
00086   *dsc = fsdp_description_new();
00087   obj = *dsc;
00088 
00089   /* TODO: add sanity checks */
00090   obj->version = sdp_version;
00091   obj->o_username = strdup(owner_username);
00092   obj->o_session_id = strdup(session_id);
00093   obj->o_announcement_version = strdup(announcement_version);
00094   obj->o_network_type = owner_nt;
00095   obj->o_address_type = owner_at;
00096   obj->o_address = strdup(owner_address);
00097   obj->s_name = strdup(session_name);
00098   obj->time_periods = 
00099     calloc(TIME_PERIODS_MAX_COUNT,sizeof(fsdp_time_period_t*));
00100   obj->time_periods[0] = calloc(1,sizeof(fsdp_time_period_t));
00101   obj->time_periods[0]->start = start;
00102   obj->time_periods[0]->stop = stop;
00103   obj->time_periods_count = 1;
00104   obj->time_periods[0]->repeats = 
00105     calloc(REPEATS_MAX_COUNT,sizeof(fsdp_repeat_t*));
00106   obj->time_periods[0]->repeats_count = 0;  
00107 
00108   /* TODO: *dsc->built = 1; */
00109   return FSDPE_OK;
00110 }
00111 
00112 fsdp_error_t
00113 fsdp_format(const fsdp_description_t *dsc, char **text_description)
00114 {
00115   char *result;
00116   size_t len = 1024;
00117 
00118   if ( (NULL == dsc) || (NULL == text_description) )
00119     return FSDPE_INVALID_PARAMETER;
00120 
00121   result = malloc(len);
00122 
00123   /* iterative calls to */
00124   fsdp_format_bounded(dsc,result,len);
00125 
00126   *text_description = result;
00127 
00128   return FSDPE_OK;
00129 }
00130 
00131 fsdp_error_t
00132 fsdp_format_bounded(const fsdp_description_t *dsc, char *text_description, 
00133               size_t maxsize)
00134 {  
00135   unsigned int i = 0, len = 0;
00136 
00137   if ( (NULL == dsc) || (NULL == text_description) )
00138     return FSDPE_INVALID_PARAMETER;
00139 
00140   /* while ( len < maxsize ) */
00141   /* `v=' line (protocol version) */
00142   len += snprintf(text_description,100,"v=0\r\n");
00143 
00144   /***************************************************************************/
00145   /* A) parse session-level description                                      */
00146   /***************************************************************************/
00147   /* o= line (owner/creator and session identifier). */
00148   len += snprintf(text_description + len,100,
00149             "o=%s %s %s %2s %3s %s\r\n",dsc->o_username,
00150             dsc->o_session_id,dsc->o_announcement_version,
00151             network_type_strings[dsc->c_network_type],
00152             address_type_strings[dsc->o_address_type],dsc->o_address);
00153   
00154   /* s= line (session name). */
00155   len += snprintf(text_description + len,100,"s=%s\r\n",dsc->s_name);
00156 
00157   /* `i=' line (session information) [optional] */
00158   if ( dsc->i_information != NULL )
00159     len += snprintf(text_description + len,100,"i=%s\r\n",dsc->i_information);
00160 
00161   /* `u=' line (URI of description) [optional] */
00162   if ( dsc->u_uri != NULL )
00163     len += snprintf(text_description + len,100,"u=%s\r\n",dsc->u_uri);
00164 
00165   /* `e=' lines (email address) [zero or more] */
00166   for ( i = 0; i < dsc->emails_count; i++ ) {
00167     len += snprintf(text_description + len,100,"e=%s\r\n",dsc->emails[i]);
00168   }
00169 
00170   /* `p=' lines (phone number) [zero or more] */
00171   for ( i = 0; i < dsc->phones_count; i++ ) {
00172     len += snprintf(text_description + len,100,"p=%s\r\n",dsc->phones[i]);   
00173   }
00174 
00175   /* `c=' line (connection information - not required if included in all media) [optional] */
00176   if ( FSDP_NETWORK_TYPE_UNDEFINED != dsc->c_network_type ) {
00177     if ( 0 == dsc->c_address.address_ttl ) {
00178       len += snprintf(text_description + len,100,"c=%s %s %s\r\n",
00179                 network_type_strings[dsc->c_network_type],
00180                 address_type_strings[dsc->c_address_type],
00181                 dsc->c_address.address);
00182     } else {
00183       if ( 0 == dsc->c_address.address_count ) {
00184      len += snprintf(text_description + len,100,"c=%s %s %s/%d\r\n",
00185                network_type_strings[dsc->c_network_type],
00186                address_type_strings[dsc->c_address_type],
00187                dsc->c_address.address,dsc->c_address.address_ttl);
00188       } else {
00189      len += snprintf(text_description + len,100,"c=%s %s %s/%d/%d\r\n",
00190                network_type_strings[dsc->c_network_type],
00191                address_type_strings[dsc->c_address_type],
00192                dsc->c_address.address,dsc->c_address.address_ttl,
00193                dsc->c_address.address_count);
00194       }
00195     }
00196   }
00197 
00198   /* `b=' lines (bandwidth information) [optional] */
00199   for (i = 0; i < dsc->bw_modifiers_count; i++) {
00200     fsdp_bw_modifier_type_t mt = dsc->bw_modifiers[i].b_mod_type;
00201     if ( FSDP_BW_MOD_TYPE_UNKNOWN == mt ) {
00202       len += snprintf(text_description + len,100,"b=%s:%lu\r\n",
00203                 dsc->bw_modifiers[i].b_unknown_bw_modt,
00204                 dsc->bw_modifiers[i].b_value);
00205     } else {
00206       len += snprintf(text_description + len,100,"b=%s:%lu\r\n",
00207                 bw_mod_type_strings[mt],dsc->bw_modifiers[i].b_value);
00208     }      
00209   } 
00210 
00211   /* `t=' lines (time the session is active) [1 or more] */
00212   for (i = 0; i < dsc->time_periods_count; i++) {
00213     unsigned int j;
00214     len += snprintf(text_description + len,100,"t=%lu %lu\r\n",
00215               dsc->time_periods[i]->start + NTP_EPOCH_OFFSET,
00216               dsc->time_periods[i]->stop + NTP_EPOCH_OFFSET);
00217     
00218     /* `r' lines [zero or more repeat times for each t=] */
00219     for ( j = 0; j < dsc->time_periods[i]->repeats_count; j++ ) {
00220       fsdp_repeat_t *repeat = dsc->time_periods[i]->repeats[j];
00221       len += snprintf(text_description + len,100,"r=%lu %lu %lu\r\n",
00222                 repeat->interval, repeat->duration, 
00223                 repeat->offsets[0]); /* FIX offsets */
00224     }
00225   }
00226   
00227   /* `z=' line (time zone adjustments) [zero or more] */
00228   if ( NULL != dsc->timezone_adj)
00229     len += snprintf(text_description + len,100,"z=%s\r\n",dsc->timezone_adj);
00230 
00231   /* `k=' line (encryption key) [optional] */
00232   if ( FSDP_ENCRYPTION_METHOD_UNDEFINED == dsc->k_encryption_method ) {
00233     ;
00234   } else if ( FSDP_ENCRYPTION_METHOD_PROMPT == dsc->k_encryption_method ) {
00235     len += snprintf(text_description + len,100,"k=prompt\r\n");
00236   } else {
00237     len += snprintf(text_description + len,100,"k=%s:%s\r\n",
00238               encryption_method_strings[dsc->k_encryption_method],
00239               dsc->k_encryption_content);
00240   }
00241 
00242   /* `a=' lines (zero or more session attribute lines) [optional] */
00243   {
00244     unsigned int j;
00245 
00246     if ( NULL != dsc->a_str_attributes[FSDP_SESSION_STR_ATT_CATEGORY] )
00247       len += snprintf(text_description + len,100,"a=cat:%s\r\n",
00248                 dsc->a_str_attributes[FSDP_SESSION_STR_ATT_CATEGORY]);
00249 
00250     if ( NULL != dsc->a_str_attributes[FSDP_SESSION_STR_ATT_CATEGORY] )
00251       len += snprintf(text_description + len,100,"a=keywds:%s\r\n",
00252                 dsc->a_str_attributes[FSDP_SESSION_STR_ATT_CATEGORY]);
00253 
00254     if ( NULL != dsc->a_str_attributes[FSDP_SESSION_STR_ATT_TOOL] )
00255       len += snprintf(text_description + len,100,"a=tool:%s\r\n",
00256                 dsc->a_str_attributes[FSDP_SESSION_STR_ATT_TOOL]);
00257 
00258     for ( j = 0; j < dsc->a_rtpmaps_count; j++ ) {
00259       fsdp_rtpmap_t *rtpmap = dsc->a_rtpmaps[j];
00260       if ( NULL == rtpmap->parameters )
00261      len += snprintf(text_description + len,100,
00262                "a=rtpmap:%s %s/%u\r\n",
00263                rtpmap->pt,rtpmap->encoding_name,rtpmap->clock_rate);
00264       else
00265      len += snprintf(text_description + len,100,
00266                "a=rtpmap:%s %s/%u/%s\r\n",
00267                rtpmap->pt,rtpmap->encoding_name,rtpmap->clock_rate,
00268                rtpmap->parameters);
00269     }
00270 
00271     if ( FSDP_SENDRECV_UNDEFINED != dsc->a_sendrecv_mode )
00272       len += snprintf(text_description + len,100,"a=%s\r\n",
00273                 sendrecv_mode_strings[dsc->a_sendrecv_mode]);
00274 
00275     if ( FSDP_SESSION_TYPE_UNDEFINED != dsc->a_type )
00276       len += snprintf(text_description + len,100,"a=type:%s\r\n",
00277                 session_type_strings[dsc->a_type]);
00278 
00279     if ( NULL != dsc->a_str_attributes[FSDP_SESSION_STR_ATT_CHARSET] )
00280       len += snprintf(text_description + len,100,"a=charset:%s\r\n",
00281                 dsc->a_str_attributes[FSDP_SESSION_STR_ATT_CHARSET]);
00282 
00283     for ( j = 0; j < dsc->a_sdplangs_count; j++ ) {
00284       len += snprintf(text_description + len,100,"a=sdplang:%s\r\n",
00285                 dsc->a_sdplangs[j]);
00286     }
00287 
00288     for ( j = 0; j < dsc->a_langs_count; j++ ) {
00289       len += snprintf(text_description + len,100,"a=lang:%s\r\n",
00290                 dsc->a_langs[j]);
00291     }
00292 
00293     /* attributes not recognized by FreeSDP */
00294     for ( j = 0; j < dsc->unidentified_attributes_count; j++ ) {
00295       len += snprintf(text_description + len,100,"a=%s\r\n",
00296                 dsc->unidentified_attributes[j]);
00297     }
00298   }
00299 
00300   /***************************************************************************/
00301   /* B) print media-level descriptions                                       */
00302   /***************************************************************************/
00303   for ( i = 0; i < dsc->media_announcements_count; i++) {
00304     unsigned int j;
00305     fsdp_media_announcement_t *ann = dsc->media_announcements[i];
00306     {       /* `m=' line (media name, transport address and format list) */
00307       if ( 0 == ann->port_count )
00308      len += snprintf(text_description + len,100,"m=%s %d %s",
00309                media_strings[ann->media_type],ann->port,
00310                tp_strings[ann->transport]);
00311       else
00312      len += snprintf(text_description + len,100,"m=%s %d/%d %s",
00313                media_strings[ann->media_type],
00314                ann->port,ann->port_count,
00315                tp_strings[ann->transport]);
00316      
00317       for ( j = 0; j < ann->formats_count; j++ )
00318      len += snprintf(text_description + len,100," %s",ann->formats[j]);
00319       len += snprintf(text_description + len,100,"\r\n");
00320     }
00321 
00322     if ( ann->i_title != NULL )
00323       len += snprintf(text_description + len,100,"i=%s\r\n",
00324                 ann->i_title);
00325     
00326     if ( FSDP_NETWORK_TYPE_UNDEFINED != ann->c_network_type ) {
00327       if ( 0 == ann->c_address.address_ttl ) {
00328      len += snprintf(text_description + len,100,"c=%s %s %s\r\n",
00329                network_type_strings[ann->c_network_type],
00330                address_type_strings[ann->c_address_type],
00331                ann->c_address.address);
00332       } else {
00333      if ( 0 == ann->c_address.address_count ) {
00334        len += snprintf(text_description + len,100,"c=%s %s %s/%d\r\n",
00335                  network_type_strings[ann->c_network_type],
00336                  address_type_strings[dsc->c_address_type],
00337                  ann->c_address.address,ann->c_address.address_ttl);
00338      } else {
00339        len += snprintf(text_description + len,100,"c=%s %s %s/%d/%d\r\n",
00340                  network_type_strings[ann->c_network_type],
00341                  address_type_strings[ann->c_address_type],
00342                  ann->c_address.address,ann->c_address.address_ttl,
00343                  ann->c_address.address_count);
00344      }
00345       }
00346     }
00347   
00348     /* `b=' lines (bandwidth information) [optional] */
00349     for (j = 0; j < ann->bw_modifiers_count; j++) {
00350       fsdp_bw_modifier_type_t mt = ann->bw_modifiers[j].b_mod_type;
00351       if ( FSDP_BW_MOD_TYPE_UNKNOWN == mt )
00352      len += snprintf(text_description + len,100,"b=%s:%lu\r\n",
00353                ann->bw_modifiers[j].b_unknown_bw_modt,
00354                ann->bw_modifiers[j].b_value);
00355       else
00356      len += snprintf(text_description + len,100,"b=%s:%lu\r\n",
00357                bandwidth_modifier_strings[ann->bw_modifiers[j].b_mod_type],
00358                ann->bw_modifiers[j].b_value);
00359     }
00360 
00361     /* `k=' line (encryption key) [optional] */
00362     if ( FSDP_ENCRYPTION_METHOD_UNDEFINED == ann->k_encryption_method ) {
00363       ;
00364     } else if ( FSDP_ENCRYPTION_METHOD_PROMPT == ann->k_encryption_method ) {
00365       len += snprintf(text_description + len,100,"k=prompt\r\n");
00366     } else {
00367       len += snprintf(text_description + len,100,"k=%s:%s\r\n",
00368                 encryption_method_strings[ann->k_encryption_method],
00369                 ann->k_encryption_content);
00370     }
00371 
00372     /* `a=' lines (zero or more media attribute lines) [optional] */
00373     if ( 0 != ann->a_ptime )
00374       len += snprintf(text_description + len,100,"a=ptime:%lu\r\n",
00375                 ann->a_ptime);
00376 
00377     if ( 0 != ann->a_maxptime )
00378       len += snprintf(text_description + len,100,"a=maxptime:%lu\r\n",
00379                 ann->a_maxptime);
00380 
00381     for ( j = 0; j < ann->a_rtpmaps_count; j++ ) {
00382       fsdp_rtpmap_t *rtpmap = ann->a_rtpmaps[j];
00383       if ( NULL == rtpmap->parameters )
00384      len += snprintf(text_description + len,100,
00385                "a=rtpmap:%s %s/%u\r\n",
00386                rtpmap->pt,rtpmap->encoding_name,rtpmap->clock_rate);
00387       else
00388      len += snprintf(text_description + len,100,
00389                "a=rtpmap:%s %s/%u/%s\r\n",
00390                rtpmap->pt,rtpmap->encoding_name,rtpmap->clock_rate,
00391                rtpmap->parameters);
00392     }
00393 
00394     if ( FSDP_ORIENT_UNDEFINED != ann->a_orient )
00395       len += snprintf(text_description + len,100,"a=orient:%s\r\n",
00396                 orient_strings[ann->a_orient]);
00397 
00398     if ( FSDP_SENDRECV_UNDEFINED != ann->a_sendrecv_mode )
00399       len += snprintf(text_description + len,100,"a=%s\r\n",
00400                 sendrecv_mode_strings[ann->a_sendrecv_mode]);
00401 
00402     for ( j = 0; j < ann->a_sdplangs_count; j++ ) {
00403       len += snprintf(text_description + len,100,"a=sdplang:%s\r\n",
00404                 ann->a_sdplangs[j]);
00405     }
00406 
00407     for ( j = 0; j < ann->a_langs_count; j++ ) {
00408       len += snprintf(text_description + len,100,"a=lang:%s\r\n",
00409                 ann->a_langs[j]);
00410     }
00411 
00412     if ( 0.0 != ann->a_framerate )
00413       len += snprintf(text_description + len,100,"a=framerate:%f\r\n",
00414                 ann->a_framerate);
00415 
00416     if ( 0 != ann->a_quality )
00417       len += snprintf(text_description + len,100,"a=quality:%ul\r\n",
00418                 ann->a_quality);
00419     
00420     for ( j = 0; j < ann->a_fmtps_count; j++ ) {
00421       len += snprintf(text_description + len,100,"a=lang:%s\r\n",
00422                 ann->a_fmtps[j]);
00423     }
00424 
00425     if ( NULL != ann->a_rtcp_address ) {
00426       len += snprintf(text_description + len,100,"a=rtcp:%u %s %s %s\r\n",
00427                 ann->a_rtcp_port,
00428                 network_type_strings[ann->a_rtcp_network_type],
00429                 address_type_strings[ann->a_rtcp_address_type],
00430                 ann->a_rtcp_address);
00431     }
00432 
00433     /* attributes not recognized by FreeSDP */
00434     for ( j = 0; j < ann->unidentified_attributes_count; j++ ) {
00435       len += snprintf(text_description + len,100,"a=%s\r\n",
00436                 ann->unidentified_attributes[j]);
00437     }
00438   }
00439 
00440   /* this should be a macro: */
00441   if ( (len + 5) > maxsize ) 
00442     return FSDPE_BUFFER_OVERFLOW;
00443   len += 5;
00444   
00445   /* strncpy */
00446   return FSDPE_INTERNAL_ERROR;
00447 }
00448 
00449 
00450 fsdp_error_t
00451 fsdp_set_information(fsdp_description_t *dsc, const char *info)
00452 {
00453   if ( (NULL == dsc) || (NULL == info) )
00454     return FSDPE_INVALID_PARAMETER;
00455 
00456   if ( NULL != dsc->i_information )
00457     free(dsc->i_information);
00458   dsc->i_information = strdup(info);
00459   return FSDPE_OK;
00460 }
00461 
00462 fsdp_error_t
00463 fsdp_set_uri(fsdp_description_t *dsc, const char *uri)
00464 {
00465   if ( (NULL == dsc) || (NULL == uri) )
00466     return FSDPE_INVALID_PARAMETER;
00467 
00468   if ( NULL != dsc->u_uri )
00469     free(dsc->u_uri);
00470   dsc->u_uri = strdup(uri);
00471   return FSDPE_OK;
00472 }
00473 
00474 fsdp_error_t
00475 fsdp_add_email(fsdp_description_t *dsc, char *email)
00476 {
00477   if ( (NULL == dsc) || (NULL == email) ) {
00478     return FSDPE_INVALID_PARAMETER;
00479   } 
00480   if ( NULL == dsc->emails ) {
00481     dsc->emails_count = 0;
00482     dsc->emails = calloc(EMAILS_MAX_COUNT,sizeof(char*));
00483   }
00484   if ( dsc->emails_count < EMAILS_MAX_COUNT ) /* FIX */
00485     dsc->emails[dsc->emails_count++] = strdup(email);
00486 
00487   return FSDPE_OK;
00488 }
00489 
00490 fsdp_error_t
00491 fsdp_add_phone(fsdp_description_t *dsc, char *phone)
00492 {
00493   if ( (NULL == dsc) || (NULL == phone) ) {
00494     return FSDPE_INVALID_PARAMETER;
00495   } 
00496   if ( NULL == dsc->phones ) {
00497     dsc->phones_count = 0;
00498     dsc->phones = calloc(PHONES_MAX_COUNT,sizeof(char*));
00499   }
00500   if ( dsc->phones_count < PHONES_MAX_COUNT ) /* FIX */
00501     dsc->phones[dsc->phones_count++] = strdup(phone);
00502 
00503   return FSDPE_OK;
00504 }
00505 
00506 fsdp_error_t
00507 fsdp_set_conn_address(fsdp_description_t *dsc, fsdp_network_type_t nt,
00508                 fsdp_address_type_t at, const char *address,
00509                 unsigned int address_ttl, unsigned int address_count)
00510 {
00511   if ( (NULL == dsc) || (NULL == address) ) {
00512     return FSDPE_INVALID_PARAMETER;
00513   }
00514   dsc->c_network_type = nt;
00515   dsc->c_address_type = at;
00516   if ( NULL != dsc->c_address.address )
00517     free(dsc->c_address.address);
00518   dsc->c_address.address = strdup(address);
00519   dsc->c_address.address_ttl = address_ttl;
00520   dsc->c_address.address_count = address_count;
00521   return FSDPE_OK;
00522 }
00523 
00524 fsdp_error_t
00525 fsdp_add_bw_info(fsdp_description_t *dsc,
00526            fsdp_bw_modifier_type_t mt, unsigned long int value, 
00527            const char *unk_bmt)
00528 {
00529   if ( (NULL == dsc) ||
00530        ((FSDP_BW_MOD_TYPE_UNKNOWN == mt) && (NULL == unk_bmt)) ) {
00531     return FSDPE_INVALID_PARAMETER;
00532   }
00533   if ( NULL == dsc->bw_modifiers ) {
00534     dsc->bw_modifiers_count = 0;
00535     dsc->bw_modifiers = 
00536       calloc(BW_MODIFIERS_MAX_COUNT,sizeof(fsdp_bw_modifier_t));
00537   }
00538   if ( dsc->bw_modifiers_count < BW_MODIFIERS_MAX_COUNT ) { /* FIX */
00539     fsdp_bw_modifier_t *bwm = &(dsc->bw_modifiers[dsc->bw_modifiers_count]);
00540     bwm->b_mod_type = mt;
00541     bwm->b_value = value;
00542     if ( FSDP_BW_MOD_TYPE_UNKNOWN == mt) {
00543       bwm->b_unknown_bw_modt = strdup(unk_bmt);
00544     }
00545     dsc->bw_modifiers_count++;
00546   }
00547 
00548   return FSDPE_OK;
00549 }
00550 
00551 fsdp_error_t
00552 fsdp_add_period(fsdp_description_t *dsc, time_t start, time_t stop)
00553 {
00554   if ( (NULL == dsc) )
00555     return FSDPE_INVALID_PARAMETER;
00556   
00557   if ( dsc->time_periods_count < TIME_PERIODS_MAX_COUNT ) {
00558     /* FIX */
00559     fsdp_time_period_t *period;
00560     dsc->time_periods[dsc->time_periods_count] = 
00561       calloc(1,sizeof(fsdp_time_period_t));
00562     period = dsc->time_periods[dsc->time_periods_count];
00563     period->start = start;
00564     period->stop = stop;
00565     dsc->time_periods_count++;
00566   }
00567   return FSDPE_OK;
00568 }
00569 
00570 fsdp_error_t
00571 fsdp_add_repeat(fsdp_description_t *dsc, unsigned long int interval,
00572           unsigned long int duration, const char *offsets)
00573 {
00574   fsdp_time_period_t *period;
00575   
00576   if ( (NULL == dsc) || (NULL == offsets) )
00577     return FSDPE_INVALID_PARAMETER;
00578 
00579   period = dsc->time_periods[dsc->time_periods_count];
00580   if ( NULL == period->repeats ) {
00581     period->repeats_count = 0;
00582     period->repeats = 
00583       calloc(REPEATS_MAX_COUNT,sizeof(fsdp_repeat_t*));
00584   }
00585   if ( period->repeats_count < REPEATS_MAX_COUNT ) {
00586     /* FIX */
00587     fsdp_repeat_t *repeat;
00588     period->repeats[period->repeats_count] = calloc(1,sizeof(fsdp_repeat_t));
00589     repeat = period->repeats[period->repeats_count];
00590     repeat->interval = interval;
00591     repeat->duration = duration;
00592     /* TODO repeat->offsets = strdup(offsets); */
00593     repeat->offsets = NULL;
00594     period->repeats_count++;
00595   }
00596   return FSDPE_OK;
00597 }
00598 
00599 fsdp_error_t
00600 fsdp_set_encryption(fsdp_description_t *dsc, fsdp_encryption_method_t emethod,
00601               const char *ekey)
00602 {
00603   if ( (NULL == dsc) || 
00604        ((FSDP_ENCRYPTION_METHOD_PROMPT != emethod) 
00605      && (NULL == ekey)) ) {
00606     return FSDPE_INVALID_PARAMETER;
00607   }
00608   dsc->k_encryption_method = emethod;
00609   if ( NULL != dsc->k_encryption_content )
00610     free(dsc->k_encryption_content);
00611   if ( FSDP_ENCRYPTION_METHOD_PROMPT != emethod )
00612     dsc->k_encryption_content = strdup(ekey);
00613   return FSDPE_OK;
00614 }
00615 
00616 fsdp_error_t
00617 fsdp_set_timezone_adj(fsdp_description_t *dsc, const char *adj)
00618 {
00619   if ( (NULL == dsc) || (NULL == adj) )
00620     return FSDPE_INVALID_PARAMETER;
00621   if ( NULL != dsc->timezone_adj )
00622     free(dsc->timezone_adj);
00623   dsc->timezone_adj = strdup(adj);
00624   return FSDPE_OK;
00625 }
00626 
00627 fsdp_error_t
00628 fsdp_set_str_att(fsdp_description_t *dsc, fsdp_session_str_att_t att,
00629            const char *value)
00630 {
00631   if ( NULL == dsc )
00632     return FSDPE_INVALID_PARAMETER;
00633   if ( att <= FSDP_LAST_SESSION_STR_ATT ) {
00634     if ( NULL != dsc->a_str_attributes[att] )
00635       free(dsc->a_str_attributes[att]);
00636     dsc->a_str_attributes[att] = strdup(value);
00637   } else 
00638     return FSDPE_INVALID_PARAMETER;
00639   return FSDPE_OK;
00640 }
00641 
00642 fsdp_error_t
00643 fsdp_add_sdplang(fsdp_description_t *dsc, const char* lang)
00644 {
00645   if ( (NULL == dsc) || (NULL == lang) )
00646     return FSDPE_INVALID_PARAMETER;
00647   
00648   if ( NULL == dsc->a_sdplangs ) {
00649     dsc->a_sdplangs_count = 0;
00650     dsc->a_sdplangs = 
00651       calloc(SDPLANGS_MAX_COUNT,sizeof(char*));
00652   }
00653   if ( dsc->a_sdplangs_count < SDPLANGS_MAX_COUNT ) {
00654     dsc->a_sdplangs[dsc->a_sdplangs_count] = strdup(lang);
00655     dsc->a_sdplangs_count++;
00656   }
00657   return FSDPE_OK;
00658 }
00659 
00660 fsdp_error_t
00661 fsdp_add_lang(fsdp_description_t *dsc, const char* lang)
00662 {
00663   if ( (NULL == dsc) || (NULL == lang) )
00664     return FSDPE_INVALID_PARAMETER;
00665   
00666   if ( NULL == dsc->a_langs ) {
00667     dsc->a_langs_count = 0;
00668     dsc->a_langs = calloc(SDPLANGS_MAX_COUNT,sizeof(char*));
00669   }
00670   if ( dsc->a_langs_count < SDPLANGS_MAX_COUNT ) {
00671     dsc->a_langs[dsc->a_langs_count] = strdup(lang);
00672     dsc->a_langs_count++;
00673   }
00674   return FSDPE_OK;
00675 }
00676 
00677 fsdp_error_t
00678 fsdp_add_rtpmap(fsdp_description_t *dsc, const char* payload_type,
00679           const char *encoding_name, unsigned int rate, 
00680           const char *parameters)
00681 {
00682   if ( (NULL == dsc) || (NULL == encoding_name) )
00683     return FSDPE_INVALID_PARAMETER;
00684 
00685   if ( NULL == dsc->a_rtpmaps ) {
00686     dsc->a_rtpmaps_count = 0;
00687     dsc->a_rtpmaps = calloc(MEDIA_RTPMAPS_MAX_COUNT,sizeof(fsdp_rtpmap_t*));
00688   }
00689   {
00690     unsigned int c = dsc->a_rtpmaps_count;
00691     if ( c < MEDIA_RTPMAPS_MAX_COUNT ) {
00692       dsc->a_rtpmaps[c] = calloc(1,sizeof(fsdp_rtpmap_t));
00693       dsc->a_rtpmaps[c]->pt = strdup(payload_type);
00694       dsc->a_rtpmaps[c]->encoding_name = strdup(encoding_name);
00695       dsc->a_rtpmaps[c]->clock_rate = rate;
00696       if ( NULL != parameters )
00697      dsc->a_rtpmaps[c]->parameters = strdup(parameters);
00698       dsc->a_rtpmaps_count++;
00699     }
00700   }
00701   return FSDPE_OK;
00702 }
00703 
00704 fsdp_error_t
00705 fsdp_set_sendrecv(fsdp_description_t *dsc, fsdp_sendrecv_mode_t mode)
00706 {
00707   if ( (NULL == dsc) )
00708     return FSDPE_INVALID_PARAMETER;
00709   dsc->a_sendrecv_mode = mode;
00710   return FSDPE_OK;
00711 }
00712 
00713 fsdp_error_t
00714 fsdp_set_session_type(fsdp_description_t *dsc, fsdp_session_type_t type)
00715 {
00716   if ( (NULL == dsc) )
00717     return FSDPE_INVALID_PARAMETER;
00718   dsc->a_type = type;
00719   return FSDPE_OK;
00720 }
00721 
00722 fsdp_error_t
00723 fsdp_add_media(fsdp_description_t *dsc, fsdp_media_description_t *const mdsc)
00724 {
00725   if ( (NULL == dsc) || (NULL == mdsc) )
00726     return FSDPE_INVALID_PARAMETER;
00727   if ( NULL == dsc->media_announcements ) {
00728     dsc->media_announcements_count = 0;
00729     dsc->media_announcements = 
00730       calloc(MEDIA_ANNOUNCEMENTS_MAX_COUNT,sizeof(fsdp_media_announcement_t*));
00731   }
00732   if ( dsc->media_announcements_count < MEDIA_ANNOUNCEMENTS_MAX_COUNT )
00733     dsc->media_announcements[dsc->media_announcements_count++] = mdsc; /* FIX */
00734   return FSDPE_OK;
00735 }
00736 
00737 fsdp_error_t
00738 fsdp_make_media(fsdp_media_description_t **mdsc, fsdp_media_t type,
00739           unsigned int port, unsigned int port_count, 
00740           fsdp_transport_protocol_t tp, const char *format)
00741 {
00742   fsdp_media_description_t *obj;
00743 
00744   if ( (NULL == mdsc) || (NULL == format) )
00745     return FSDPE_INVALID_PARAMETER;
00746 
00747   *mdsc = calloc(1,sizeof(fsdp_media_description_t));
00748   obj = *mdsc;
00749   obj->media_type = type;
00750   obj->port = port;
00751   obj->port_count = port_count;
00752   obj->transport = tp;
00753   /* TODO: check that format is valid */
00754   obj->formats = calloc(MEDIA_FORMATS_MAX_COUNT,sizeof(char*));
00755   obj->formats[0] = strdup(format);
00756   obj->formats_count = 1;
00757   obj->a_rtpmaps = NULL;
00758   return FSDPE_OK;
00759 }
00760 
00761 fsdp_error_t
00762 fsdp_add_media_format(fsdp_media_description_t *mdsc, const char *format)
00763 {
00764   if ( (NULL == mdsc) || (NULL == format) ) {
00765     return FSDPE_INVALID_PARAMETER;
00766   }
00767   if ( mdsc->formats_count < MEDIA_FORMATS_MAX_COUNT ) {
00768     mdsc->formats[mdsc->formats_count] = strdup(format);
00769     mdsc->formats_count++;
00770   }
00771   return FSDPE_OK;
00772 }
00773 
00774 fsdp_error_t
00775 fsdp_set_media_title(fsdp_media_description_t *mdsc, const char *title)
00776 {
00777   if ( (NULL == mdsc) || (NULL == title) ) {
00778     return FSDPE_INVALID_PARAMETER;
00779   }
00780   if ( NULL != mdsc->i_title )
00781     free(mdsc->i_title);
00782   mdsc->i_title = strdup(title);
00783   return FSDPE_OK;
00784 }
00785 
00786 fsdp_error_t
00787 fsdp_set_media_conn_address(fsdp_media_description_t *mdsc,
00788                    fsdp_network_type_t nt, fsdp_address_type_t at, 
00789                    const char *address, unsigned int address_ttl, 
00790                    unsigned int address_count)
00791 {
00792   if ( (NULL == mdsc) || (NULL == address) ) {
00793     return FSDPE_INVALID_PARAMETER;
00794   }
00795   mdsc->c_network_type = nt;
00796   mdsc->c_address_type = at;
00797   if ( NULL != mdsc->c_address.address )
00798     free(mdsc->c_address.address);
00799   mdsc->c_address.address = strdup(address);
00800   mdsc->c_address.address_ttl = address_ttl;
00801   mdsc->c_address.address_count = address_count;
00802   return FSDPE_OK;
00803 }
00804 
00805 fsdp_error_t
00806 fsdp_add_media_bw_info(fsdp_media_description_t *mdsc, 
00807                  fsdp_bw_modifier_type_t mt,
00808                  unsigned long int value, const char *unk_bmt)
00809 {
00810   if ( (NULL == mdsc) ||
00811        ((FSDP_BW_MOD_TYPE_UNKNOWN == mt) && (NULL == unk_bmt)) ) {
00812     return FSDPE_INVALID_PARAMETER;
00813   }
00814   if ( NULL == mdsc->bw_modifiers ) {
00815     mdsc->bw_modifiers_count = 0;
00816     mdsc->bw_modifiers = calloc(BW_MODIFIERS_MAX_COUNT,sizeof(char*));
00817   }
00818   if ( mdsc->bw_modifiers_count < BW_MODIFIERS_MAX_COUNT ) { /* FIX */
00819     fsdp_bw_modifier_t *bwm = &(mdsc->bw_modifiers[mdsc->bw_modifiers_count]);
00820     bwm->b_mod_type = mt;
00821     bwm->b_value = value;
00822     if ( FSDP_BW_MOD_TYPE_UNKNOWN== mt) {
00823       bwm->b_unknown_bw_modt = strdup(unk_bmt);
00824     }
00825     mdsc->bw_modifiers_count++;
00826   }
00827   return FSDPE_OK;
00828 }
00829 
00830 fsdp_error_t
00831 fsdp_set_media_encryption(fsdp_media_description_t *mdsc,
00832                  fsdp_encryption_method_t emethod, const char *ekey)
00833 {
00834   if ( (NULL == mdsc) || 
00835        ((FSDP_ENCRYPTION_METHOD_PROMPT != emethod) 
00836      && (NULL == ekey)) ) {
00837     return FSDPE_INVALID_PARAMETER;
00838   }
00839   mdsc->k_encryption_method = emethod;
00840   if ( NULL != mdsc->k_encryption_content )
00841     free(mdsc->k_encryption_content);
00842   if ( FSDP_ENCRYPTION_METHOD_PROMPT != emethod )
00843     mdsc->k_encryption_content = strdup(ekey);
00844   return FSDPE_OK;
00845 }
00846 
00847 fsdp_error_t
00848 fsdp_set_media_ptime(fsdp_media_description_t *mdsc, unsigned int ptime)
00849 {
00850   if ( (NULL == mdsc) )
00851     return FSDPE_INVALID_PARAMETER;
00852   mdsc->a_ptime = ptime;
00853   return FSDPE_OK;
00854 }
00855 
00856 fsdp_error_t
00857 fsdp_set_media_maxptime(fsdp_media_description_t *mdsc, unsigned int maxptime)
00858 {
00859   if ( (NULL == mdsc) )
00860     return FSDPE_INVALID_PARAMETER;
00861   mdsc->a_maxptime = maxptime;
00862   return FSDPE_OK;
00863 }
00864 
00865 
00866 fsdp_error_t
00867 fsdp_add_media_fmtp(fsdp_media_description_t *mdsc, const char* fmtp)
00868 {
00869   if ( (NULL == mdsc) || (NULL == fmtp) )
00870     return FSDPE_INVALID_PARAMETER;
00871   
00872   if ( NULL == mdsc->a_fmtps ) {
00873     mdsc->a_fmtps_count = 0;
00874     mdsc->a_fmtps = calloc(SDPLANGS_MAX_COUNT,sizeof(char*));
00875   }
00876   if ( mdsc->a_fmtps_count < SDPLANGS_MAX_COUNT ) {
00877     mdsc->a_fmtps[mdsc->a_fmtps_count] = strdup(fmtp);
00878     mdsc->a_fmtps_count++;
00879   }
00880   return FSDPE_OK;
00881 }
00882 
00883 fsdp_error_t
00884 fsdp_set_media_orient(fsdp_media_description_t *mdsc, fsdp_orient_t orient)
00885 {
00886   if ( (NULL == mdsc) )
00887     return FSDPE_INVALID_PARAMETER;
00888   mdsc->a_orient = orient;
00889   return FSDPE_OK;
00890 }
00891 
00892 fsdp_error_t
00893 fsdp_add_media_sdplang(fsdp_media_description_t *mdsc, const char* lang)
00894 {
00895   if ( (NULL == mdsc) || (NULL == lang) )
00896     return FSDPE_INVALID_PARAMETER;
00897   
00898   if ( NULL == mdsc->a_sdplangs ) {
00899     mdsc->a_sdplangs_count = 0;
00900     mdsc->a_sdplangs = 
00901       calloc(SDPLANGS_MAX_COUNT,sizeof(char*));
00902   }
00903   if ( mdsc->a_sdplangs_count < SDPLANGS_MAX_COUNT ) {
00904     mdsc->a_sdplangs[mdsc->a_sdplangs_count] = strdup(lang);
00905     mdsc->a_sdplangs_count++;
00906   }
00907   return FSDPE_OK;
00908 }
00909 
00910 fsdp_error_t
00911 fsdp_add_media_lang(fsdp_media_description_t *mdsc, const char* lang)
00912 {
00913   if ( (NULL == mdsc) || (NULL == lang) )
00914     return FSDPE_INVALID_PARAMETER;
00915   
00916   if ( NULL == mdsc->a_langs ) {
00917     mdsc->a_langs_count = 0;
00918     mdsc->a_langs = calloc(SDPLANGS_MAX_COUNT,sizeof(char*));
00919   }
00920   if ( mdsc->a_langs_count < SDPLANGS_MAX_COUNT ) {
00921     mdsc->a_langs[mdsc->a_langs_count] = strdup(lang);
00922     mdsc->a_langs_count++;
00923   }
00924   return FSDPE_OK;
00925 }
00926 
00927 fsdp_error_t
00928 fsdp_set_media_sendrecv(fsdp_media_description_t *mdsc,
00929                fsdp_sendrecv_mode_t mode)
00930 {
00931   if ( (NULL == mdsc) )
00932     return FSDPE_INVALID_PARAMETER;
00933   mdsc->a_sendrecv_mode = mode;
00934   return FSDPE_OK;
00935 }
00936 
00937 fsdp_error_t
00938 fsdp_set_media_framerate(fsdp_media_description_t *mdsc, float rate)
00939 {
00940   if ( (NULL == mdsc) )
00941     return FSDPE_INVALID_PARAMETER;
00942   mdsc->a_framerate = rate;
00943   return FSDPE_OK;
00944 }
00945 
00946 fsdp_error_t
00947 fsdp_set_media_quality(fsdp_media_description_t *mdsc, unsigned int q)
00948 {
00949   if ( (NULL == mdsc) )
00950     return FSDPE_INVALID_PARAMETER;
00951   mdsc->a_quality = q;
00952   return FSDPE_OK;
00953 }
00954 
00955 fsdp_error_t
00956 fsdp_add_media_rtpmap(fsdp_media_description_t *mdsc, const char* payload_type,
00957                 const char *encoding_name, unsigned int rate, 
00958                 const char *parameters)
00959 {
00960   if ( (NULL == mdsc) || (NULL == encoding_name) )
00961     return FSDPE_INVALID_PARAMETER;
00962 
00963   if ( NULL == mdsc->a_rtpmaps ) {
00964     mdsc->a_rtpmaps_count = 0;
00965     mdsc->a_rtpmaps = calloc(MEDIA_RTPMAPS_MAX_COUNT,sizeof(fsdp_rtpmap_t*));
00966   }
00967   {
00968     unsigned int c = mdsc->a_rtpmaps_count;
00969     if ( c < MEDIA_RTPMAPS_MAX_COUNT ) {
00970       mdsc->a_rtpmaps[c] = calloc(1,sizeof(fsdp_rtpmap_t));
00971       mdsc->a_rtpmaps[c]->pt = strdup(payload_type);
00972       mdsc->a_rtpmaps[c]->encoding_name = strdup(encoding_name);
00973       mdsc->a_rtpmaps[c]->clock_rate = rate;
00974       if ( NULL != parameters )
00975      mdsc->a_rtpmaps[c]->parameters = strdup(parameters);
00976       mdsc->a_rtpmaps_count++;
00977     }
00978   }
00979   return FSDPE_OK;
00980 }
00981 
00982 fsdp_error_t
00983 fsdp_set_media_rtcp(fsdp_media_description_t *mdsc, unsigned int port,
00984               fsdp_network_type_t nt, fsdp_address_type_t at,
00985               const char *address)
00986 {
00987   if ( (NULL == mdsc) || (NULL == address) )
00988     return FSDPE_INVALID_PARAMETER;
00989   mdsc->a_rtcp_port = port;
00990   mdsc->a_rtcp_network_type = nt;
00991   mdsc->a_rtcp_address_type = at;
00992   if ( NULL != mdsc->a_rtcp_address )
00993     free(mdsc->a_rtcp_address);
00994   mdsc->a_rtcp_address = strdup(address);
00995   return FSDPE_OK;
00996 }

Generated on Sun Jan 18 21:12:43 2004 for FreeSDP by doxygen 1.3.4