Begin adding MSRP media layer (sender, receiver and media handler).

Add new SDP utility functions (HOLD, RESUME ...)
This commit is contained in:
bossiel 2010-03-24 01:57:57 +00:00
parent edd9503f12
commit f7bcd56d67
85 changed files with 1203 additions and 210 deletions

View File

@ -0,0 +1,55 @@
/*
* Copyright (C) 2009 Mamadou Diop.
*
* Contact: Mamadou Diop <diopmamadou@yahoo.fr>
*
* This file is part of Open Source Doubango Framework.
*
* DOUBANGO is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* DOUBANGO is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with DOUBANGO.
*
*/
/**@file tmsrp_media.h
* @brief MSRP Media definition.
*
* @author Mamadou Diop <diopmamadou(at)yahoo.fr>
*
* @date Created: Sat Nov 8 16:54:58 2009 mdiop
*/
#ifndef TINYMSRP_MEDIA_H
#define TINYMSRP_MEDIA_H
#include "tinyMSRP_config.h"
#include "tinyMEDIA/tmedia.h"
#include "tsdp.h"
TMSRP_BEGIN_DECLS
#define TMSRP_MEDIA(self) ((tmsrp_media_t*)(self))
typedef struct tmsrp_media_s
{
TMED_DECLARE_MEDIA;
tsdp_ctx_handle_t* sdp_ctx;
}
tmsrp_media_t;
const tsk_object_def_t *tmsrp_media_def_t;
const tmedia_plugin_def_t *tmsrp_media_plugin_def_t;
TMSRP_END_DECLS
#endif /* TINYMSRP_MEDIA_H */

View File

@ -0,0 +1,165 @@
/*
* Copyright (C) 2009 Mamadou Diop.
*
* Contact: Mamadou Diop <diopmamadou@yahoo.fr>
*
* This file is part of Open Source Doubango Framework.
*
* DOUBANGO is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* DOUBANGO is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with DOUBANGO.
*
*/
/**@file tmsrp_media.c
* @brief MSRP Media definition.
*
* @author Mamadou Diop <diopmamadou(at)yahoo.fr>
*
* @date Created: Sat Nov 8 16:54:58 2009 mdiop
*/
#include "tinyMSRP/session/tmsrp_media.h"
#include "tsk_string.h"
#include "tsk_memory.h"
#include "tsk_debug.h"
int tmsrp_media_set_params(tmedia_t* self, const tsk_params_L_t* params)
{
tmsrp_media_t *msrp = TMSRP_MEDIA(self);
TSK_DEBUG_INFO("tmsrp_media_set_params");
return 0;
}
int tmsrp_media_start(tmedia_t* self)
{
tmsrp_media_t *msrp = TMSRP_MEDIA(self);
TSK_DEBUG_INFO("tmsrp_media_start");
return 0;
}
int tmsrp_media_pause(tmedia_t* self)
{
tmsrp_media_t *msrp = TMSRP_MEDIA(self);
TSK_DEBUG_INFO("tmsrp_media_pause");
return 0;
}
int tmsrp_media_stop(tmedia_t* self)
{
tmsrp_media_t *msrp = TMSRP_MEDIA(self);
TSK_DEBUG_INFO("tmsrp_media_stop");
return 0;
}
char* tmsrp_media_get_local_offer(tmedia_t* self)
{
tmsrp_media_t *msrp = TMSRP_MEDIA(self);
TSK_DEBUG_INFO("tmsrp_media_get_local_offer");
return tsk_null;
}
char* tmsrp_media_get_negotiated_offer(tmedia_t* self)
{
tmsrp_media_t *msrp = TMSRP_MEDIA(self);
TSK_DEBUG_INFO("tmsrp_media_get_negotiated_offer");
return tsk_null;
}
int tmsrp_media_set_remote_offer(tmedia_t* self, const char* offer)
{
tmsrp_media_t *msrp = TMSRP_MEDIA(self);
TSK_DEBUG_INFO("tmsrp_media_set_remote_offer");
return 0;
}
//========================================================
// Dummy media object definition
//
static void* tmsrp_media_create(tsk_object_t *self, va_list * app)
{
tmsrp_media_t *msrp = self;
if(msrp)
{
// Parameters include at least the media name
tmedia_init(TMEDIA(msrp), va_arg(*app, const char*));
TMEDIA(msrp)->protocol = tsk_strdup("TCP/MSRP");
msrp->sdp_ctx = TSDP_CTX_CREATE();
}
else{
TSK_DEBUG_ERROR("Failed to create new dummy media.");
}
return self;
}
static void* tmsrp_media_destroy(tsk_object_t *self)
{
tmsrp_media_t *msrp = self;
if(msrp){
tmedia_deinit(TMEDIA(msrp));
TSK_OBJECT_SAFE_FREE(msrp->sdp_ctx);
}
else{
TSK_DEBUG_ERROR("Null dummy media.");
}
return self;
}
static int tmsrp_media_cmp(const tsk_object_t *obj1, const tsk_object_t *obj2)
{
return -1;
}
static const tsk_object_def_t tmsrp_media_def_s =
{
sizeof(tmsrp_media_t),
tmsrp_media_create,
tmsrp_media_destroy,
tmsrp_media_cmp
};
const tsk_object_def_t *tmsrp_media_def_t = &tmsrp_media_def_s;
//========================================================
// Dummy media plugin definition
//
static const tmedia_plugin_def_t tmsrp_media_plugin_def_s =
{
&tmsrp_media_def_s,
"message",
tmsrp_media_set_params,
tmsrp_media_start,
tmsrp_media_pause,
tmsrp_media_stop,
tmsrp_media_get_local_offer,
tmsrp_media_get_negotiated_offer,
tmsrp_media_set_remote_offer
};
const tmedia_plugin_def_t *tmsrp_media_plugin_def_t = &tmsrp_media_plugin_def_s;

View File

@ -35,7 +35,8 @@
#define RUN_TEST_ALL 0
#define RUN_TEST_URI 0
#define RUN_TEST_PARSER 1
#define RUN_TEST_PARSER 0
#define RUN_TEST_SESSION 1
#ifdef _WIN32_WCE
int _tmain(int argc, _TCHAR* argv[])
@ -58,5 +59,9 @@ int main()
test_parser();
#endif
#if RUN_TEST_ALL || RUN_TEST_SESSION
test_session();
#endif
}
}

View File

@ -208,6 +208,10 @@
RelativePath=".\test_parser.h"
>
</File>
<File
RelativePath=".\test_session.h"
>
</File>
<File
RelativePath=".\test_uri.h"
>

View File

@ -0,0 +1,30 @@
/*
* Copyright (C) 2009 Mamadou Diop.
*
* Contact: Mamadou Diop <diopmamadou@yahoo.fr>
*
* This file is part of Open Source Doubango Framework.
*
* DOUBANGO is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* DOUBANGO is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with DOUBANGO.
*
*/
#ifndef _TEST_MSRPSESSION_H
#define _TEST_MSRPSESSION_H
void test_session()
{
}
#endif /* _TEST_MSRPSESSION_H */

View File

@ -11,6 +11,10 @@ Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tinyHTTP", "..\tinyHTTP\tin
EndProject
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tinyNET", "..\tinyNET\tinyNET.vcproj", "{7522A458-92F4-4259-B906-E84C2A65D9F1}"
EndProject
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tinyMEDIA", "..\tinyMEDIA\tinyMEDIA.vcproj", "{52814B0D-7DCA-45B8-9A16-8B147040D619}"
EndProject
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tinySDP", "..\tinySDP\tinySDP.vcproj", "{E45DB518-6562-4033-80E8-60030F0B169F}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Win32 = Debug|Win32
@ -61,6 +65,18 @@ Global
{7522A458-92F4-4259-B906-E84C2A65D9F1}.Release|Windows Mobile 5.0 Pocket PC SDK (ARMV4I).ActiveCfg = Release|Windows Mobile 5.0 Pocket PC SDK (ARMV4I)
{7522A458-92F4-4259-B906-E84C2A65D9F1}.Release|Windows Mobile 5.0 Pocket PC SDK (ARMV4I).Build.0 = Release|Windows Mobile 5.0 Pocket PC SDK (ARMV4I)
{7522A458-92F4-4259-B906-E84C2A65D9F1}.Release|Windows Mobile 5.0 Pocket PC SDK (ARMV4I).Deploy.0 = Release|Windows Mobile 5.0 Pocket PC SDK (ARMV4I)
{52814B0D-7DCA-45B8-9A16-8B147040D619}.Debug|Win32.ActiveCfg = Debug|Win32
{52814B0D-7DCA-45B8-9A16-8B147040D619}.Debug|Win32.Build.0 = Debug|Win32
{52814B0D-7DCA-45B8-9A16-8B147040D619}.Debug|Windows Mobile 5.0 Pocket PC SDK (ARMV4I).ActiveCfg = Debug|Win32
{52814B0D-7DCA-45B8-9A16-8B147040D619}.Release|Win32.ActiveCfg = Release|Win32
{52814B0D-7DCA-45B8-9A16-8B147040D619}.Release|Win32.Build.0 = Release|Win32
{52814B0D-7DCA-45B8-9A16-8B147040D619}.Release|Windows Mobile 5.0 Pocket PC SDK (ARMV4I).ActiveCfg = Release|Win32
{E45DB518-6562-4033-80E8-60030F0B169F}.Debug|Win32.ActiveCfg = Debug|Win32
{E45DB518-6562-4033-80E8-60030F0B169F}.Debug|Win32.Build.0 = Debug|Win32
{E45DB518-6562-4033-80E8-60030F0B169F}.Debug|Windows Mobile 5.0 Pocket PC SDK (ARMV4I).ActiveCfg = Debug|Win32
{E45DB518-6562-4033-80E8-60030F0B169F}.Release|Win32.ActiveCfg = Release|Win32
{E45DB518-6562-4033-80E8-60030F0B169F}.Release|Win32.Build.0 = Release|Win32
{E45DB518-6562-4033-80E8-60030F0B169F}.Release|Windows Mobile 5.0 Pocket PC SDK (ARMV4I).ActiveCfg = Release|Win32
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE

View File

@ -41,7 +41,7 @@
<Tool
Name="VCCLCompilerTool"
Optimization="0"
AdditionalIncludeDirectories="&quot;$(DOUBANGO_HOME)\thirdparties\win32\include&quot;;&quot;$(DOUBANGO_HOME)\tinySAK\src&quot;;&quot;$(DOUBANGO_HOME)\tinyMSRP\include&quot;;&quot;$(DOUBANGO_HOME)\tinyHTTP\include&quot;"
AdditionalIncludeDirectories="&quot;$(DOUBANGO_HOME)\thirdparties\win32\include&quot;;&quot;$(DOUBANGO_HOME)\tinySAK\src&quot;;&quot;$(DOUBANGO_HOME)\tinyMSRP\include&quot;;&quot;$(DOUBANGO_HOME)\tinyHTTP\include&quot;;&quot;$(DOUBANGO_HOME)\tinyMEDIA\include&quot;;&quot;$(DOUBANGO_HOME)\tinySDP\include&quot;"
PreprocessorDefinitions="DEBUG_LEVEL=DEBUG_LEVEL_INFO;WIN32;_DEBUG;_WINDOWS;_USRDLL;TINYMSRP_EXPORTS"
MinimalRebuild="true"
BasicRuntimeChecks="3"
@ -63,7 +63,7 @@
/>
<Tool
Name="VCLinkerTool"
AdditionalDependencies="$(OutDir)\tinySAK.lib $(OutDir)\tinyHTTP.lib"
AdditionalDependencies="$(OutDir)\tinySAK.lib $(OutDir)\tinyHTTP.lib $(OutDir)\tinySDP.lib $(OutDir)\tinyMEDIA.lib"
LinkIncremental="2"
GenerateDebugInformation="true"
SubSystem="2"
@ -280,6 +280,26 @@
>
</File>
</Filter>
<Filter
Name="session"
>
<File
RelativePath=".\include\tinyMSRP\session\tmsrp_media.h"
>
</File>
<File
RelativePath=".\include\tinyMSRP\session\tmsrp_receiver.h"
>
</File>
<File
RelativePath=".\include\tinyMSRP\session\tmsrp_sender.h"
>
</File>
<File
RelativePath=".\include\tinyMSRP\session\tmsrp_session.h"
>
</File>
</Filter>
</Filter>
<Filter
Name="source(*.c)"
@ -382,6 +402,26 @@
>
</File>
</Filter>
<Filter
Name="session"
>
<File
RelativePath=".\src\session\tmsrp_media.c"
>
</File>
<File
RelativePath=".\src\session\tmsrp_receiver.c"
>
</File>
<File
RelativePath=".\src\session\tmsrp_sender.c"
>
</File>
<File
RelativePath=".\src\session\tmsrp_session.c"
>
</File>
</Filter>
</Filter>
<Filter
Name="ragel(*.rl)"

View File

@ -147,15 +147,15 @@ typedef void tsk_object_t;
typedef struct tsk_object_def_s
{
size_t size; /**< The size of the object. */
void* (* constructor) (tsk_object_t *, va_list *); /**< Pointer to the constructor. */
void* (* destructor) (tsk_object_t *); /**< Pointer to the destructor. */
tsk_object_t* (* constructor) (tsk_object_t *, va_list *); /**< Pointer to the constructor. */
tsk_object_t* (* destructor) (tsk_object_t *); /**< Pointer to the destructor. */
int (* objcmp) (const tsk_object_t *, const tsk_object_t *); /**< Pointer to the comparator. */
}
tsk_object_def_t;
TINYSAK_API tsk_object_t* tsk_object_new(const tsk_object_def_t *objdef, ...);
TINYSAK_API tsk_object_t* tsk_object_new2(const tsk_object_def_t *objdef, va_list* ap);
TINYSAK_API size_t tsk_object_sizeof(const void *tsk_object_t);
TINYSAK_API size_t tsk_object_sizeof(const tsk_object_t *);
TINYSAK_API int tsk_object_cmp(const void *self, const tsk_object_t *object);
TINYSAK_API tsk_object_t* tsk_object_ref(tsk_object_t *self);
TINYSAK_API tsk_object_t* tsk_object_unref(tsk_object_t *self);

View File

@ -111,7 +111,7 @@ tsk_sha1context_t;
*/
TINYSAK_API tsk_sha1_errcode_t tsk_sha1reset(tsk_sha1context_t *);
TINYSAK_API tsk_sha1_errcode_t tsk_sha1input(tsk_sha1context_t *, const uint8_t *, unsigned int32_t);
TINYSAK_API tsk_sha1_errcode_t tsk_sha1input(tsk_sha1context_t *, const uint8_t *, unsigned length);
TINYSAK_API tsk_sha1_errcode_t tsk_sha1result(tsk_sha1context_t *, tsk_sha1digest_t Message_Digest);
TINYSAK_API void tsk_sha1final(uint8_t *Message_Digest, tsk_sha1context_t *context);
TINYSAK_API tsk_sha1_errcode_t tsk_sha1compute(const char* input, size_t size, tsk_sha1string_t *result);

View File

@ -126,13 +126,7 @@ char* tsk_strdup(const char *s1)
return tsk_null;
}
/**
* @fn char* tsk_strndup(const char *s1, size_t n)
*
* @brief Duplicates the first @a n chars of @a s1.
*
* @author Mamadou
* @date 1/16/2010
/** Duplicates the first @a n chars of @a s1.
*
* @param [in,out] s1 The string to duplicate.
* @param n The number of chars to copy to the new string.
@ -141,12 +135,15 @@ char* tsk_strdup(const char *s1)
**/
char* tsk_strndup(const char *s1, size_t n)
{
char *ret = 0;
size_t len = strlen(s1);
size_t nret = (n > len) ? (len) : (n);
char *ret = tsk_null;
ret = tsk_calloc((nret+1), sizeof(uint8_t));
memcpy(ret, s1, nret);
if(s1 && n){
size_t len = strlen(s1);
size_t nret = (n > len) ? (len) : (n);
ret = tsk_calloc((nret+1), sizeof(uint8_t));
memcpy(ret, s1, nret);
}
return ret;
}

View File

@ -49,6 +49,7 @@
MinimalRebuild="true"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
DisableLanguageExtensions="false"
UsePrecompiledHeader="0"
WarningLevel="3"
WarnAsError="true"
@ -207,6 +208,7 @@
PreprocessorDefinitions="WIN32;NDEBUG;_WINDOWS;_USRDLL;TINYSAK_EXPORTS"
RuntimeLibrary="2"
EnableFunctionLevelLinking="true"
DisableLanguageExtensions="true"
UsePrecompiledHeader="0"
WarningLevel="3"
WarnAsError="true"

View File

@ -110,6 +110,7 @@ typedef tsk_list_t tsdp_headers_L_t; /**< List of @ref tsdp_header_t elements. *
================================*/
int tsdp_header_rank_cmp(const tsdp_header_t*, const tsdp_header_t*);
TINYSDP_API tsdp_header_t* tsdp_header_clone(const tsdp_header_t*);
TINYSDP_API char tsdp_header_get_name(tsdp_header_type_t type);
TINYSDP_API char tsdp_header_get_nameex(const tsdp_header_t *self);
TINYSDP_API int tsdp_header_tostring(const tsdp_header_t *self, tsk_buffer_t *output);

View File

@ -43,6 +43,8 @@ TSDP_BEGIN_DECLS
#define TSDP_HEADER_A_CREATE(field, value) tsk_object_new(TSDP_HEADER_A_VA_ARGS(field, value))
#define TSDP_HEADER_A_CREATE_NULL() TSDP_HEADER_A_CREATE(tsk_null, tsk_null)
#define TSDP_HEADER_A(self) ((tsdp_header_A_t*)(self))
////////////////////////////////////////////////////////////////////////////////////////////////////
/// @struct
///
@ -67,7 +69,7 @@ typedef tsk_list_t tsdp_headers_A_L_t;
tsdp_header_A_t *tsdp_header_A_parse(const char *data, size_t size);
TINYSDP_GEXTERN const void *tsdp_header_A_def_t;
TINYSDP_GEXTERN const tsk_object_def_t *tsdp_header_A_def_t;
TSDP_END_DECLS

View File

@ -66,7 +66,7 @@ typedef tsk_list_t tsdp_headers_B_L_t;
tsdp_header_B_t *tsdp_header_B_parse(const char *data, size_t size);
TINYSDP_GEXTERN const void *tsdp_header_B_def_t;
TINYSDP_GEXTERN const tsk_object_def_t *tsdp_header_B_def_t;
TSDP_END_DECLS

View File

@ -71,7 +71,7 @@ typedef tsk_list_t tsdp_headers_C_L_t;
tsdp_header_C_t *tsdp_header_C_parse(const char *data, size_t size);
TINYSDP_GEXTERN const void *tsdp_header_C_def_t;
TINYSDP_GEXTERN const tsk_object_def_t *tsdp_header_C_def_t;
TSDP_END_DECLS

View File

@ -63,7 +63,7 @@ typedef tsk_list_t tsdp_headers_Dummy_L_t;
tsdp_header_Dummy_t *tsdp_header_Dummy_parse(const char *data, size_t size);
TINYSDP_GEXTERN const void *tsdp_header_Dummy_def_t;
TINYSDP_GEXTERN const tsk_object_def_t *tsdp_header_Dummy_def_t;
TSDP_END_DECLS

View File

@ -66,7 +66,7 @@ typedef tsk_list_t tsdp_headers_E_L_t;
tsdp_header_E_t *tsdp_header_E_parse(const char *data, size_t size);
TINYSDP_GEXTERN const void *tsdp_header_E_def_t;
TINYSDP_GEXTERN const tsk_object_def_t *tsdp_header_E_def_t;
TSDP_END_DECLS

View File

@ -62,7 +62,7 @@ typedef tsk_list_t tsdp_headers_I_L_t;
tsdp_header_I_t *tsdp_header_I_parse(const char *data, size_t size);
TINYSDP_GEXTERN const void *tsdp_header_I_def_t;
TINYSDP_GEXTERN const tsk_object_def_t *tsdp_header_I_def_t;
TSDP_END_DECLS

View File

@ -68,7 +68,7 @@ typedef tsk_list_t tsdp_headers_K_L_t;
tsdp_header_K_t *tsdp_header_K_parse(const char *data, size_t size);
TINYSDP_GEXTERN const void *tsdp_header_K_def_t;
TINYSDP_GEXTERN const tsk_object_def_t *tsdp_header_K_def_t;
TSDP_END_DECLS

View File

@ -49,7 +49,9 @@ TSDP_BEGIN_DECLS
*/
#define TSDP_HEADER_M_VA_ARGS(media, port, proto) tsdp_header_M_def_t, (const char*)media, (uint32_t)port, (const char*)proto
#define TSDP_HEADER_M_CREATE(media, port, proto) tsk_object_new(TSDP_HEADER_M_VA_ARGS(media, port, proto))
#define TSDP_HEADER_M_CREATE_NULL() TSDP_HEADER_M_CREATE(tsk_null, tsk_null, tsk_null)
#define TSDP_HEADER_M_CREATE_NULL() TSDP_HEADER_M_CREATE(tsk_null, 0, tsk_null)
#define TSDP_HEADER_M(self) ((tsdp_header_M_t*)(self))
#define TSDP_FMT_VA_ARGS(fmt) tsdp_fmt_def_t, (const char*)fmt
#define TSDP_FMT_CREATE(fmt) tsk_object_new(TSDP_FMT_VA_ARGS(fmt))
@ -105,9 +107,9 @@ typedef tsk_list_t tsdp_headers_M_L_t;
tsdp_header_M_t *tsdp_header_M_parse(const char *data, size_t size);
int tsdp_header_M_add(tsdp_header_M_t* self, const tsdp_header_t* header);
//int tsdp_header_M_set(tsdp_header_M_t* self, ...);
const tsdp_header_A_t* tsdp_header_M_findA(const tsdp_header_M_t* self, const char* field);
TINYSDP_GEXTERN const void *tsdp_header_M_def_t;
TINYSDP_GEXTERN const tsk_object_def_t *tsdp_header_M_def_t;
TSDP_END_DECLS

View File

@ -113,7 +113,7 @@ tsdp_header_O_t;
tsdp_header_O_t *tsdp_header_O_parse(const char *data, size_t size);
TINYSDP_GEXTERN const void *tsdp_header_O_def_t;
TINYSDP_GEXTERN const tsk_object_def_t *tsdp_header_O_def_t;
TSDP_END_DECLS

View File

@ -66,7 +66,7 @@ typedef tsk_list_t tsdp_headers_P_L_t;
tsdp_header_P_t *tsdp_header_P_parse(const char *data, size_t size);
TINYSDP_GEXTERN const void *tsdp_header_P_def_t;
TINYSDP_GEXTERN const tsk_object_def_t *tsdp_header_P_def_t;
TSDP_END_DECLS

View File

@ -72,7 +72,7 @@ typedef tsk_list_t tsdp_headers_R_L_t;
tsdp_header_R_t *tsdp_header_R_parse(const char *data, size_t size);
TINYSDP_GEXTERN const void *tsdp_header_R_def_t;
TINYSDP_GEXTERN const tsk_object_def_t *tsdp_header_R_def_t;
TSDP_END_DECLS

View File

@ -60,7 +60,7 @@ tsdp_header_S_t;
tsdp_header_S_t *tsdp_header_S_parse(const char *data, size_t size);
TINYSDP_GEXTERN const void *tsdp_header_S_def_t;
TINYSDP_GEXTERN const tsk_object_def_t *tsdp_header_S_def_t;
TSDP_END_DECLS

View File

@ -76,7 +76,7 @@ typedef tsk_list_t tsdp_headers_T_L_t;
tsdp_header_T_t *tsdp_header_T_parse(const char *data, size_t size);
TINYSDP_GEXTERN const void *tsdp_header_T_def_t;
TINYSDP_GEXTERN const tsk_object_def_t *tsdp_header_T_def_t;
TSDP_END_DECLS

View File

@ -62,7 +62,7 @@ typedef tsk_list_t tsdp_headers_U_L_t;
tsdp_header_U_t *tsdp_header_U_parse(const char *data, size_t size);
TINYSDP_GEXTERN const void *tsdp_header_U_def_t;
TINYSDP_GEXTERN const tsk_object_def_t *tsdp_header_U_def_t;
TSDP_END_DECLS

View File

@ -66,7 +66,7 @@ typedef tsk_list_t tsdp_headers_V_L_t;
tsdp_header_V_t *tsdp_header_V_parse(const char *data, size_t size);
TINYSDP_GEXTERN const void *tsdp_header_V_def_t;
TINYSDP_GEXTERN const tsk_object_def_t *tsdp_header_V_def_t;
TSDP_END_DECLS

View File

@ -82,8 +82,8 @@ typedef tsk_list_t tsdp_headers_Z_L_t;
tsdp_header_Z_t *tsdp_header_Z_parse(const char *data, size_t size);
TINYSDP_GEXTERN const void *tsdp_header_Z_def_t;
TINYSDP_GEXTERN const void *tsdp_zone_def_t;
TINYSDP_GEXTERN const tsk_object_def_t *tsdp_header_Z_def_t;
TINYSDP_GEXTERN const tsk_object_def_t *tsdp_zone_def_t;
TSDP_END_DECLS

View File

@ -84,13 +84,22 @@ TINYSDP_API const tsdp_header_t *tsdp_message_get_headerAt(const tsdp_message_t
TINYSDP_API const tsdp_header_t *tsdp_message_get_header(const tsdp_message_t *self, tsdp_header_type_t type);
TINYSDP_API const tsdp_header_t *tsdp_message_get_headerByName(const tsdp_message_t *self, char name);
TINYSDP_API int tsdp_message_tostring(const tsdp_message_t *self, tsk_buffer_t *output);
TINYSDP_API int tsdp_message_serialize(const tsdp_message_t *self, tsk_buffer_t *output);
TINYSDP_API char* tsdp_message_tostring(const tsdp_message_t *self);
TINYSDP_API tsdp_message_t* tsdp_message_create_empty(const char* addr, tsk_bool_t ipv6);
TINYSDP_API tsdp_message_t* tsdp_message_clone(const tsdp_message_t *self);
TINYSDP_API int tsdp_message_add_media(tsdp_message_t *self, const char* media, uint32_t port, const char* proto, ...);
TINYSDP_API int tsdp_message_add_media_2(tsdp_message_t *self, const char* media, uint32_t port, const char* proto, va_list *ap);
TINYSDP_API int tsdp_message_remove_media(tsdp_message_t *self, const char* media);
TINYSDP_GEXTERN const void *tsdp_message_def_t;
// 3GPP TS 24.610 Communication HOLD
TINYSDP_API int tsdp_message_hold(tsdp_message_t* self, const char* media);
TINYSDP_API int tsdp_message_resume(tsdp_message_t* self, const char* media);
TINYSDP_GEXTERN const tsk_object_def_t *tsdp_message_def_t;
TSDP_END_DECLS

View File

@ -37,24 +37,25 @@ TSDP_BEGIN_DECLS
#define TSDP_CTX_CREATE() tsk_object_new(tsdp_ctx_def_t)
#define TSDP_LINE_S_VALUE_DEFAULT "-" /* as per RFC 3264 subclause 5 */
typedef void tsdp_ctx_handle_t;
#define TSDP_LINE_O_USERNAME_DEFAULT "doubango"
#define TSDP_LINE_O_SESSION_VER_DEFAULT 2301
#define TSDP_LINE_O_SESSION_ID_DEFAULT 1983
TINYSDP_API const tsdp_message_t* tsdp_ctx_local_get_sdp(const tsdp_ctx_handle_t* self);
TINYSDP_API int tsdp_ctx_local_create_sdp(tsdp_ctx_handle_t* self, const tsdp_message_t* local);
TINYSDP_API int tsdp_ctx_local_create_sdp_2(tsdp_ctx_handle_t* self, const char* sdp, size_t size);
TINYSDP_API int tsdp_ctx_local_add_headers(tsdp_ctx_handle_t* self, ...);
TINYSDP_API int tsdp_ctx_local_add_media(tsdp_ctx_handle_t* self, const tsdp_header_M_t* media);
TINYSDP_API int tsdp_ctx_local_add_media_2(tsdp_ctx_handle_t* self, const char* media, uint32_t port, const char* proto, ...);
typedef struct tsdp_ctx_s
{
TSK_DECLARE_OBJECT;
tsdp_caps_t* caps;
}
tsdp_ctx_t;
TINYSDP_API const tsdp_message_t* tsdp_ctx_remote_get_sdp(const tsdp_ctx_handle_t* self);
TINYSDP_API tsdp_message_t* tsdp_create_empty(const char* addr, tsk_bool_t ipv6);
TINYSDP_API const tsdp_message_t* tsdp_ctx_negotiated_get_sdp(const tsdp_ctx_handle_t* self);
TINYSDP_GEXTERN const void *tsdp_ctx_def_t;
// 3GPP TS 24.610 Communication HOLD
TINYSDP_API int tsdp_ctx_hold(tsdp_ctx_handle_t* self, const char* media);
TINYSDP_API int tsdp_ctx_resume(tsdp_ctx_handle_t* self, const char* media);
TINYSDP_GEXTERN const tsk_object_def_t *tsdp_ctx_def_t;
TSDP_END_DECLS

View File

@ -175,4 +175,4 @@ static const tsk_object_def_t tsdp_header_A_def_s =
tsdp_header_A_cmp
};
const void *tsdp_header_A_def_t = &tsdp_header_A_def_s;
const tsk_object_def_t *tsdp_header_A_def_t = &tsdp_header_A_def_s;

View File

@ -172,4 +172,4 @@ static const tsk_object_def_t tsdp_header_B_def_s =
tsdp_header_B_cmp
};
const void *tsdp_header_B_def_t = &tsdp_header_B_def_s;
const tsk_object_def_t *tsdp_header_B_def_t = &tsdp_header_B_def_s;

View File

@ -182,4 +182,4 @@ static const tsk_object_def_t tsdp_header_C_def_s =
tsdp_header_C_cmp
};
const void *tsdp_header_C_def_t = &tsdp_header_C_def_s;
const tsk_object_def_t *tsdp_header_C_def_t = &tsdp_header_C_def_s;

View File

@ -167,4 +167,4 @@ static const tsk_object_def_t tsdp_header_Dummy_def_s =
tsdp_header_Dummy_cmp
};
const void *tsdp_header_Dummy_def_t = &tsdp_header_Dummy_def_s;
const tsk_object_def_t *tsdp_header_Dummy_def_t = &tsdp_header_Dummy_def_s;

View File

@ -163,4 +163,4 @@ static const tsk_object_def_t tsdp_header_E_def_s =
tsdp_header_E_cmp
};
const void *tsdp_header_E_def_t = &tsdp_header_E_def_s;
const tsk_object_def_t *tsdp_header_E_def_t = &tsdp_header_E_def_s;

View File

@ -163,4 +163,4 @@ static const tsk_object_def_t tsdp_header_I_def_s =
tsdp_header_I_cmp
};
const void *tsdp_header_I_def_t = &tsdp_header_I_def_s;
const tsk_object_def_t *tsdp_header_I_def_t = &tsdp_header_I_def_s;

View File

@ -163,4 +163,4 @@ static const tsk_object_def_t tsdp_header_K_def_s =
tsdp_header_K_cmp
};
const void *tsdp_header_K_def_t = &tsdp_header_K_def_s;
const tsk_object_def_t *tsdp_header_K_def_t = &tsdp_header_K_def_s;

View File

@ -264,6 +264,24 @@ int tsdp_header_M_add(tsdp_header_M_t* self, const tsdp_header_t* header)
return 0;
}
const tsdp_header_A_t* tsdp_header_M_findA(const tsdp_header_M_t* self, const char* field)
{
const tsk_list_item_t *item;
if(!self){
return tsk_null;
}
tsk_list_foreach(item, self->Attributes)
{
if(tsk_strequals(TSDP_HEADER_A(item->data)->field, field)){
return TSDP_HEADER_A(item->data);
}
}
return tsk_null;
}
//
//int tsdp_header_M_set(tsdp_header_M_t* self, ...)
//{
@ -372,4 +390,4 @@ static const tsk_object_def_t tsdp_header_M_def_s =
tsdp_header_M_cmp
};
const void *tsdp_header_M_def_t = &tsdp_header_M_def_s;
const tsk_object_def_t *tsdp_header_M_def_t = &tsdp_header_M_def_s;

View File

@ -204,4 +204,4 @@ static const tsk_object_def_t tsdp_header_O_def_s =
tsdp_header_O_cmp
};
const void *tsdp_header_O_def_t = &tsdp_header_O_def_s;
const tsk_object_def_t *tsdp_header_O_def_t = &tsdp_header_O_def_s;

View File

@ -163,4 +163,4 @@ static const tsk_object_def_t tsdp_header_P_def_s =
tsdp_header_P_cmp
};
const void *tsdp_header_P_def_t = &tsdp_header_P_def_s;
const tsk_object_def_t *tsdp_header_P_def_t = &tsdp_header_P_def_s;

View File

@ -202,4 +202,4 @@ static const tsk_object_def_t tsdp_header_R_def_s =
tsdp_header_R_cmp
};
const void *tsdp_header_R_def_t = &tsdp_header_R_def_s;
const tsk_object_def_t *tsdp_header_R_def_t = &tsdp_header_R_def_s;

View File

@ -161,4 +161,4 @@ static const tsk_object_def_t tsdp_header_S_def_s =
tsdp_header_S_cmp
};
const void *tsdp_header_S_def_t = &tsdp_header_S_def_s;
const tsk_object_def_t *tsdp_header_S_def_t = &tsdp_header_S_def_s;

View File

@ -218,4 +218,4 @@ static const tsk_object_def_t tsdp_header_T_def_s =
tsdp_header_T_cmp
};
const void *tsdp_header_T_def_t = &tsdp_header_T_def_s;
const tsk_object_def_t *tsdp_header_T_def_t = &tsdp_header_T_def_s;

View File

@ -162,4 +162,4 @@ static const tsk_object_def_t tsdp_header_U_def_s =
tsdp_header_U_cmp
};
const void *tsdp_header_U_def_t = &tsdp_header_U_def_s;
const tsk_object_def_t *tsdp_header_U_def_t = &tsdp_header_U_def_s;

View File

@ -161,4 +161,4 @@ static const tsk_object_def_t tsdp_header_V_def_s =
tsdp_header_V_cmp
};
const void *tsdp_header_V_def_t = &tsdp_header_V_def_s;
const tsk_object_def_t *tsdp_header_V_def_t = &tsdp_header_V_def_s;

View File

@ -211,7 +211,7 @@ static const tsk_object_def_t tsdp_header_Z_def_s =
tsdp_header_Z_cmp
};
const void *tsdp_header_Z_def_t = &tsdp_header_Z_def_s;
const tsk_object_def_t *tsdp_header_Z_def_t = &tsdp_header_Z_def_s;
@ -256,4 +256,4 @@ static const tsk_object_def_t tsdp_zone_def_s =
0
};
const void *tsdp_zone_def_t = &tsdp_zone_def_s;
const tsk_object_def_t *tsdp_zone_def_t = &tsdp_zone_def_s;

View File

@ -41,6 +41,14 @@ int tsdp_header_rank_cmp(const tsdp_header_t* hdr1, const tsdp_header_t* hdr2)
}
}
tsdp_header_t* tsdp_header_clone(const tsdp_header_t* self)
{
if(self){
return self->clone(self);
}
return tsk_null;
}
/** Gets the name of the SDP header with a type equal to @a type.
* @param type The @a type of the header for which to retrieve the name.
*

View File

@ -363,4 +363,4 @@ static const tsk_object_def_t tsdp_header_A_def_s =
tsdp_header_A_cmp
};
const void *tsdp_header_A_def_t = &tsdp_header_A_def_s;
const tsk_object_def_t *tsdp_header_A_def_t = &tsdp_header_A_def_s;

View File

@ -347,4 +347,4 @@ static const tsk_object_def_t tsdp_header_B_def_s =
tsdp_header_B_cmp
};
const void *tsdp_header_B_def_t = &tsdp_header_B_def_s;
const tsk_object_def_t *tsdp_header_B_def_t = &tsdp_header_B_def_s;

View File

@ -356,4 +356,4 @@ static const tsk_object_def_t tsdp_header_C_def_s =
tsdp_header_C_cmp
};
const void *tsdp_header_C_def_t = &tsdp_header_C_def_s;
const tsk_object_def_t *tsdp_header_C_def_t = &tsdp_header_C_def_s;

View File

@ -337,4 +337,4 @@ static const tsk_object_def_t tsdp_header_Dummy_def_s =
tsdp_header_Dummy_cmp
};
const void *tsdp_header_Dummy_def_t = &tsdp_header_Dummy_def_s;
const tsk_object_def_t *tsdp_header_Dummy_def_t = &tsdp_header_Dummy_def_s;

View File

@ -328,4 +328,4 @@ static const tsk_object_def_t tsdp_header_E_def_s =
tsdp_header_E_cmp
};
const void *tsdp_header_E_def_t = &tsdp_header_E_def_s;
const tsk_object_def_t *tsdp_header_E_def_t = &tsdp_header_E_def_s;

View File

@ -328,4 +328,4 @@ static const tsk_object_def_t tsdp_header_I_def_s =
tsdp_header_I_cmp
};
const void *tsdp_header_I_def_t = &tsdp_header_I_def_s;
const tsk_object_def_t *tsdp_header_I_def_t = &tsdp_header_I_def_s;

View File

@ -328,4 +328,4 @@ static const tsk_object_def_t tsdp_header_K_def_s =
tsdp_header_K_cmp
};
const void *tsdp_header_K_def_t = &tsdp_header_K_def_s;
const tsk_object_def_t *tsdp_header_K_def_t = &tsdp_header_K_def_s;

View File

@ -456,6 +456,24 @@ int tsdp_header_M_add(tsdp_header_M_t* self, const tsdp_header_t* header)
return 0;
}
const tsdp_header_A_t* tsdp_header_M_findA(const tsdp_header_M_t* self, const char* field)
{
const tsk_list_item_t *item;
if(!self){
return tsk_null;
}
tsk_list_foreach(item, self->Attributes)
{
if(tsk_strequals(TSDP_HEADER_A(item->data)->field, field)){
return TSDP_HEADER_A(item->data);
}
}
return tsk_null;
}
//
//int tsdp_header_M_set(tsdp_header_M_t* self, ...)
//{
@ -564,4 +582,4 @@ static const tsk_object_def_t tsdp_header_M_def_s =
tsdp_header_M_cmp
};
const void *tsdp_header_M_def_t = &tsdp_header_M_def_s;
const tsk_object_def_t *tsdp_header_M_def_t = &tsdp_header_M_def_s;

View File

@ -393,4 +393,4 @@ static const tsk_object_def_t tsdp_header_O_def_s =
tsdp_header_O_cmp
};
const void *tsdp_header_O_def_t = &tsdp_header_O_def_s;
const tsk_object_def_t *tsdp_header_O_def_t = &tsdp_header_O_def_s;

View File

@ -328,4 +328,4 @@ static const tsk_object_def_t tsdp_header_P_def_s =
tsdp_header_P_cmp
};
const void *tsdp_header_P_def_t = &tsdp_header_P_def_s;
const tsk_object_def_t *tsdp_header_P_def_t = &tsdp_header_P_def_s;

View File

@ -381,4 +381,4 @@ static const tsk_object_def_t tsdp_header_R_def_s =
tsdp_header_R_cmp
};
const void *tsdp_header_R_def_t = &tsdp_header_R_def_s;
const tsk_object_def_t *tsdp_header_R_def_t = &tsdp_header_R_def_s;

View File

@ -326,4 +326,4 @@ static const tsk_object_def_t tsdp_header_S_def_s =
tsdp_header_S_cmp
};
const void *tsdp_header_S_def_t = &tsdp_header_S_def_s;
const tsk_object_def_t *tsdp_header_S_def_t = &tsdp_header_S_def_s;

View File

@ -368,4 +368,4 @@ static const tsk_object_def_t tsdp_header_T_def_s =
tsdp_header_T_cmp
};
const void *tsdp_header_T_def_t = &tsdp_header_T_def_s;
const tsk_object_def_t *tsdp_header_T_def_t = &tsdp_header_T_def_s;

View File

@ -327,4 +327,4 @@ static const tsk_object_def_t tsdp_header_U_def_s =
tsdp_header_U_cmp
};
const void *tsdp_header_U_def_t = &tsdp_header_U_def_s;
const tsk_object_def_t *tsdp_header_U_def_t = &tsdp_header_U_def_s;

View File

@ -320,4 +320,4 @@ static const tsk_object_def_t tsdp_header_V_def_s =
tsdp_header_V_cmp
};
const void *tsdp_header_V_def_t = &tsdp_header_V_def_s;
const tsk_object_def_t *tsdp_header_V_def_t = &tsdp_header_V_def_s;

View File

@ -419,7 +419,7 @@ static const tsk_object_def_t tsdp_header_Z_def_s =
tsdp_header_Z_cmp
};
const void *tsdp_header_Z_def_t = &tsdp_header_Z_def_s;
const tsk_object_def_t *tsdp_header_Z_def_t = &tsdp_header_Z_def_s;
@ -464,4 +464,4 @@ static const tsk_object_def_t tsdp_zone_def_s =
0
};
const void *tsdp_zone_def_t = &tsdp_zone_def_s;
const tsk_object_def_t *tsdp_zone_def_t = &tsdp_zone_def_s;

View File

@ -28,55 +28,142 @@
*/
#include "tsdp.h"
#include "tinySDP/headers/tsdp_header_O.h"
#include "tinySDP/headers/tsdp_header_S.h"
#include "tinySDP/headers/tsdp_header_T.h"
#include "tinySDP/headers/tsdp_header_V.h"
#include "tinySDP/parsers/tsdp_parser_message.h"
tsdp_message_t* tsdp_create_empty(const char* addr, tsk_bool_t ipv6)
// Defined in tsdp_message.c
extern int __pred_find_media_by_name(const tsk_list_item_t *item, const void *name);
typedef struct tsdp_ctx_s
{
tsdp_message_t* ret = 0;
if(!(ret = TSDP_MESSAGE_CREATE())){
return tsk_null;
}
/* RFC 3264 - 5 Generating the Initial Offer
The numeric value of the session id and version in the o line MUST be
representable with a 64 bit signed integer. The initial value of the version MUST be less than
(2**62)-1, to avoid rollovers.
*/
TSDP_MESSAGE_ADD_HEADER(ret, TSDP_HEADER_V_VA_ARGS(0));
TSDP_MESSAGE_ADD_HEADER(ret, TSDP_HEADER_O_VA_ARGS(
TSDP_LINE_O_USERNAME_DEFAULT,
TSDP_LINE_O_SESSION_ID_DEFAULT,
TSDP_LINE_O_SESSION_VER_DEFAULT,
"IN",
ipv6 ? "IP6" : "IP4",
addr));
/* RFC 3264 - 5 Generating the Initial Offer
The SDP "s=" line conveys the subject of the session, which is
reasonably defined for multicast, but ill defined for unicast. For
unicast sessions, it is RECOMMENDED that it consist of a single space
character (0x20) or a dash (-).
Unfortunately, SDP does not allow the "s=" line to be empty.
*/
TSDP_MESSAGE_ADD_HEADER(ret, TSDP_HEADER_S_VA_ARGS(TSDP_LINE_S_VALUE_DEFAULT));
/* RFC 3264 - 5 Generating the Initial Offer
The SDP "t=" line conveys the time of the session. Generally,
streams for unicast sessions are created and destroyed through
external signaling means, such as SIP. In that case, the "t=" line
SHOULD have a value of "0 0".
*/
TSDP_MESSAGE_ADD_HEADER(ret, TSDP_HEADER_T_VA_ARGS(0, 0));
TSK_DECLARE_OBJECT;
return ret;
tsdp_message_t* local;
tsdp_message_t* remote;
tsdp_message_t* negotiated;
}
tsdp_ctx_t;
const tsdp_message_t* tsdp_ctx_local_get_sdp(const tsdp_ctx_handle_t* self)
{
const tsdp_ctx_t* ctx = self;
if(ctx){
return ctx->local;
}
else return tsk_null;
}
int tsdp_ctx_local_create_sdp(tsdp_ctx_handle_t* self, const tsdp_message_t* local)
{
tsdp_ctx_t* ctx = self;
tsdp_message_t* newsdp;
if(!ctx || !local){
return -1;
}
// set new local sdp
if((newsdp = tsdp_message_clone(local))){
TSK_OBJECT_SAFE_FREE(ctx->local);
ctx->local = newsdp;
return 0;
}
else return -2;
}
int tsdp_ctx_local_create_sdp_2(tsdp_ctx_handle_t* self, const char* sdp, size_t size)
{
tsdp_ctx_t* ctx = self;
tsdp_message_t* newsdp;
if(!ctx || !sdp || !size){
return -1;
}
if((newsdp = tsdp_message_parse(sdp, size))){
TSK_OBJECT_SAFE_FREE(ctx->local);
ctx->local = newsdp;
return 0;
}
else return -2;
}
int tsdp_ctx_local_add_headers(tsdp_ctx_handle_t* self, ...)
{
tsdp_ctx_t* ctx = self;
const tsk_object_def_t* objdef;
tsdp_header_t *header;
va_list ap;
if(!ctx || !ctx->local){
return -1;
}
va_start(ap, self);
while((objdef = va_arg(ap, const tsk_object_def_t*))){
if((header = tsk_object_new2(objdef, &ap))){
tsdp_message_add_header(ctx->local, header);
TSK_OBJECT_SAFE_FREE(header);
}
}
va_end(ap);
return 0;
}
int tsdp_ctx_local_add_media(tsdp_ctx_handle_t* self, const tsdp_header_M_t* media)
{
tsdp_ctx_t* ctx = self;
if(!ctx || !media){
return -1;
}
if(ctx->local){
return tsdp_message_add_header(ctx->local, TSDP_HEADER(media));
}
else return -2;
}
int tsdp_ctx_local_add_media_2(tsdp_ctx_handle_t* self, const char* media, uint32_t port, const char* proto, ...)
{
tsdp_ctx_t* ctx = self;
va_list ap;
if(!ctx || !media || !proto){
return -1;
}
if(ctx->local){
int ret;
va_start(ap, proto);
ret = tsdp_message_add_media_2(ctx->local, media, port, proto, &ap);
va_end(ap);
return ret;
}
else return -2;
}
const tsdp_message_t* tsdp_ctx_remote_get_sdp(const tsdp_ctx_handle_t* self)
{
const tsdp_ctx_t* ctx = self;
if(ctx){
return ctx->remote;
}
else return tsk_null;
}
const tsdp_message_t* tsdp_ctx_negotiated_get_sdp(const tsdp_ctx_handle_t* self)
{
const tsdp_ctx_t* ctx = self;
if(ctx){
return ctx->negotiated;
}
else return tsk_null;
}
@ -107,7 +194,9 @@ static void* tsdp_ctx_destroy(void * self)
{
tsdp_ctx_t *ctx = self;
if(ctx){
TSK_OBJECT_SAFE_FREE(ctx->caps);
TSK_OBJECT_SAFE_FREE(ctx->local);
TSK_OBJECT_SAFE_FREE(ctx->remote);
TSK_OBJECT_SAFE_FREE(ctx->negotiated);
}
return self;
}
@ -119,4 +208,4 @@ static const tsk_object_def_t tsdp_ctx_def_s =
tsdp_ctx_destroy,
tsk_null,
};
const void *tsdp_ctx_def_t = &tsdp_ctx_def_s;
const tsk_object_def_t *tsdp_ctx_def_t = &tsdp_ctx_def_s;

View File

@ -30,8 +30,19 @@
#include "tinySDP/tsdp_message.h"
#include "tinySDP/headers/tsdp_header_O.h"
#include "tinySDP/headers/tsdp_header_S.h"
#include "tinySDP/headers/tsdp_header_T.h"
#include "tinySDP/headers/tsdp_header_V.h"
#define TSDP_LINE_S_VALUE_DEFAULT "-" /* as per RFC 3264 subclause 5 */
#define TSDP_LINE_O_USERNAME_DEFAULT "doubango"
#define TSDP_LINE_O_SESSION_VER_DEFAULT 2301
#define TSDP_LINE_O_SESSION_ID_DEFAULT 1983
/*== Predicate function to find tsdp_header_t object by type. */
static int pred_find_header_by_type(const tsk_list_item_t *item, const void *tsdp_htype)
int __pred_find_header_by_type(const tsk_list_item_t *item, const void *tsdp_htype)
{
if(item && item->data)
{
@ -43,7 +54,7 @@ static int pred_find_header_by_type(const tsk_list_item_t *item, const void *tsd
}
/*== Predicate function to find tsdp_header_t object by name. */
static int pred_find_header_by_name(const tsk_list_item_t *item, const void *name)
int __pred_find_header_by_name(const tsk_list_item_t *item, const void *name)
{
if(item && item->data && name)
{
@ -54,7 +65,7 @@ static int pred_find_header_by_name(const tsk_list_item_t *item, const void *nam
}
/*== Predicate function to find media object by name. */
static int pred_find_media_by_name(const tsk_list_item_t *item, const void *name)
int __pred_find_media_by_name(const tsk_list_item_t *item, const void *name)
{
if(item && item->data && name)
{
@ -66,6 +77,32 @@ static int pred_find_media_by_name(const tsk_list_item_t *item, const void *name
return -1;
}
/*== Add headers/fmt to the media line */
int __add_headers(tsdp_header_M_t* m, va_list *ap)
{
const tsk_object_def_t* objdef;
tsdp_header_t *header;
tsdp_fmt_t* fmt;
if(!m){
return -1;
}
while((objdef = va_arg(*ap, const tsk_object_def_t*))){
if(objdef == tsdp_fmt_def_t){
if((fmt = tsk_object_new2(objdef, ap))){
tsk_list_push_back_data(m->FMTs, (void**)&fmt);
}
}
else{
if((header = tsk_object_new2(objdef, ap))){
tsdp_header_M_add(m, header);
TSK_OBJECT_SAFE_FREE(header);
}
}
}
return 0;
}
int tsdp_message_add_header(tsdp_message_t *self, const tsdp_header_t *hdr)
{
@ -133,14 +170,14 @@ const tsdp_header_t *tsdp_message_get_headerByName(const tsdp_message_t *self, c
{
if(self && self->headers){
const tsk_list_item_t* item;
if((item = tsk_list_find_item_by_pred(self->headers, pred_find_header_by_name, &name))){
if((item = tsk_list_find_item_by_pred(self->headers, __pred_find_header_by_name, &name))){
return item->data;
}
}
return tsk_null;
}
int tsdp_message_tostring(const tsdp_message_t *self, tsk_buffer_t *output)
int tsdp_message_serialize(const tsdp_message_t *self, tsk_buffer_t *output)
{
const tsk_list_item_t* item;
@ -158,10 +195,67 @@ int tsdp_message_tostring(const tsdp_message_t *self, tsk_buffer_t *output)
return 0;
}
char* tsdp_message_tostring(const tsdp_message_t *self)
{
tsk_buffer_t* output = TSK_BUFFER_CREATE_NULL();
char* ret = tsk_null;
if(!tsdp_message_serialize(self, output)){
ret = tsk_strndup(TSK_BUFFER_DATA(output), TSK_BUFFER_SIZE(output));
}
TSK_OBJECT_SAFE_FREE(output);
return ret;
}
tsdp_message_t* tsdp_message_create_empty(const char* addr, tsk_bool_t ipv6)
{
tsdp_message_t* ret = 0;
if(!(ret = TSDP_MESSAGE_CREATE())){
return tsk_null;
}
/* RFC 3264 - 5 Generating the Initial Offer
The numeric value of the session id and version in the o line MUST be
representable with a 64 bit signed integer. The initial value of the version MUST be less than
(2**62)-1, to avoid rollovers.
*/
TSDP_MESSAGE_ADD_HEADER(ret, TSDP_HEADER_V_VA_ARGS(0));
TSDP_MESSAGE_ADD_HEADER(ret, TSDP_HEADER_O_VA_ARGS(
TSDP_LINE_O_USERNAME_DEFAULT,
TSDP_LINE_O_SESSION_ID_DEFAULT,
TSDP_LINE_O_SESSION_VER_DEFAULT,
"IN",
ipv6 ? "IP6" : "IP4",
addr));
/* RFC 3264 - 5 Generating the Initial Offer
The SDP "s=" line conveys the subject of the session, which is
reasonably defined for multicast, but ill defined for unicast. For
unicast sessions, it is RECOMMENDED that it consist of a single space
character (0x20) or a dash (-).
Unfortunately, SDP does not allow the "s=" line to be empty.
*/
TSDP_MESSAGE_ADD_HEADER(ret, TSDP_HEADER_S_VA_ARGS(TSDP_LINE_S_VALUE_DEFAULT));
/* RFC 3264 - 5 Generating the Initial Offer
The SDP "t=" line conveys the time of the session. Generally,
streams for unicast sessions are created and destroyed through
external signaling means, such as SIP. In that case, the "t=" line
SHOULD have a value of "0 0".
*/
TSDP_MESSAGE_ADD_HEADER(ret, TSDP_HEADER_T_VA_ARGS(0, 0));
return ret;
}
tsdp_message_t* tsdp_message_clone(const tsdp_message_t *self)
{
tsdp_message_t* clone = tsk_null;
tsk_list_item_t* item;
tsdp_header_t* header;
if(!self){
goto bail;
@ -169,8 +263,9 @@ tsdp_message_t* tsdp_message_clone(const tsdp_message_t *self)
if((clone = TSDP_MESSAGE_CREATE())){
tsk_list_foreach(item, self->headers){
tsdp_header_t* header = TSDP_HEADER(item->data)->clone(TSDP_HEADER(item->data));
tsk_list_push_back_data(clone->headers, (void**)&header);
if((header = tsdp_header_clone(TSDP_HEADER(item->data)))){
tsk_list_push_back_data(clone->headers, (void**)&header);
}
}
}
@ -181,41 +276,32 @@ bail:
int tsdp_message_add_media(tsdp_message_t *self, const char* media, uint32_t port, const char* proto, ...)
{
int ret = -1;
tsdp_header_M_t* m;
va_list ap;
const tsk_object_def_t* objdef;
tsdp_header_t* header;
tsdp_fmt_t* fmt;
if(!self){
goto bail;
}
if(!(m = TSDP_HEADER_M_CREATE(media, port, proto))){
goto bail;
}
int ret;
va_start(ap, proto);
while((objdef = va_arg(ap, const tsk_object_def_t*))){
if(objdef == tsdp_fmt_def_t){
if((fmt = tsk_object_new2(objdef, &ap))){
tsk_list_push_back_data(m->FMTs, (void**)&fmt);
}
}
else{
if((header = tsk_object_new2(objdef, &ap))){
tsdp_header_M_add(m, header);
TSK_OBJECT_SAFE_FREE(header);
}
}
}
ret = tsdp_message_add_media_2(self, media, port, proto, &ap);
va_end(ap);
ret = tsdp_message_add_header(self, TSDP_HEADER(m));
TSK_OBJECT_SAFE_FREE(m);
return ret;
}
bail:
int tsdp_message_add_media_2(tsdp_message_t *self, const char* media, uint32_t port, const char* proto, va_list *ap)
{
int ret = -1;
tsdp_header_M_t* m;
if(!self){
return -1;
}
if((m = TSDP_HEADER_M_CREATE(media, port, proto))){
__add_headers(m, ap);
ret = tsdp_message_add_header(self, TSDP_HEADER(m));
TSK_OBJECT_SAFE_FREE(m);
}
return ret;
}
@ -227,7 +313,7 @@ int tsdp_message_remove_media(tsdp_message_t *self, const char* media)
goto bail;
}
tsk_list_remove_item_by_pred(self->headers, pred_find_media_by_name, media);
tsk_list_remove_item_by_pred(self->headers, __pred_find_media_by_name, media);
bail:
return ret;
@ -235,11 +321,66 @@ bail:
/* ================= 3GPP TS 34.610 :: Communication HOLD (HOLD) using IP Multimedia (IM) Core ================*/
int tsdp_message_hold(tsdp_message_t* self, const char* media)
{
tsdp_header_M_t* m;
const tsdp_header_A_t* a;
const tsk_list_item_t* item;
if(!self){
return -1;
}
// 3GPP TS 34.610-900 - 4.5.2.1 Actions at the invoking UE
if((item = tsk_list_find_item_by_pred(self->headers, __pred_find_media_by_name, media))){
m = TSDP_HEADER_M(item->data);
if((a = tsdp_header_M_findA(m, "recvonly"))){
// an "inactive" SDP attribute if the stream was previously set to "recvonly" media stream
tsk_strupdate(&(TSDP_HEADER_A(a)->field), "inactive");
}
else if((a = tsdp_header_M_findA(m, "sendrecv"))){
// a "sendonly" SDP attribute if the stream was previously set to "sendrecv" media stream
tsk_strupdate(&(TSDP_HEADER_A(a)->field), "sendonly");
}
else{
// default value is sendrecv. hold on default --> sendonly
if(!(a = tsdp_header_M_findA(m, "sendonly")) && !(a = tsdp_header_M_findA(m, "inactive"))){
tsdp_header_A_t* newA;
if((newA = TSDP_HEADER_A_CREATE("sendonly", tsk_null))){
tsdp_header_M_add(m, TSDP_HEADER(newA));
TSK_OBJECT_SAFE_FREE(newA);
}
}
}
}
return 0;
}
int tsdp_message_resume(tsdp_message_t* self, const char* media)
{
tsdp_header_M_t* m;
const tsdp_header_A_t* a;
const tsk_list_item_t* item;
if(!self){
return -1;
}
// 3GPP TS 34.610-900 - 4.5.2.1 Actions at the invoking UE
if((item = tsk_list_find_item_by_pred(self->headers, __pred_find_media_by_name, media))){
m = TSDP_HEADER_M(item->data);
if((a = tsdp_header_M_findA(m, "inactive"))){
// a "recvonly" SDP attribute if the stream was previously an inactive media stream
tsk_strupdate(&(TSDP_HEADER_A(a)->field), "recvonly");
}
else if((a = tsdp_header_M_findA(m, "sendonly"))){
// a "sendrecv" SDP attribute if the stream was previously a sendonly media stream, or the attribute may be omitted, since sendrecv is the default
tsk_strupdate(&(TSDP_HEADER_A(a)->field), "sendrecv");
}
}
return 0;
}
@ -293,4 +434,4 @@ static const tsk_object_def_t tsdp_message_def_s =
tsdp_message_destroy,
tsdp_message_cmp,
};
const void *tsdp_message_def_t = &tsdp_message_def_s;
const tsk_object_def_t *tsdp_message_def_t = &tsdp_message_def_s;

View File

@ -28,12 +28,14 @@
#include "tinySDP/parsers/tsdp_parser_message.h"
#include "test_parser.h"
#include "test_soa.h"
#define RUN_TEST_LOOP 1
#define RUN_TEST_ALL 0
#define RUN_TEST_PARSER 1
#define RUN_TEST_PARSER 0
#define RUN_TEST_SOA 1
#ifdef _WIN32_WCE
@ -53,5 +55,9 @@ int main()
test_parser();
#endif
#if RUN_TEST_ALL || RUN_TEST_SOA
test_soa();
#endif
}
}

View File

@ -208,6 +208,10 @@
RelativePath=".\test_parser.h"
>
</File>
<File
RelativePath=".\test_soa.h"
>
</File>
</Filter>
</Files>
<Globals>

View File

@ -58,7 +58,7 @@
"b=B-YZ:256\r\n" \
"a=rtpmap:31 H261/90000\r\n" \
"a=rtpmap:32 MPV/90000\r\n" \
"a=sendonly\r\n"
"a=recvonly\r\n"
#define SDP_MSG2 \
"v=0\r\n"
@ -67,24 +67,27 @@
#define SDP_MSG_TO_TEST SDP_MSG1
void test_caps();
void test_holdresume();
void test_parser()
{
tsdp_message_t *message = tsk_null;
char* str;
test_caps();
test_holdresume();
//
// deserialize/serialize the message
//
if((message = tsdp_message_parse(SDP_MSG_TO_TEST, strlen(SDP_MSG_TO_TEST)))){
tsk_buffer_t *buffer = TSK_BUFFER_CREATE_NULL();
/* serialize the message */
tsdp_message_tostring(message, buffer);
TSK_DEBUG_INFO("SDP Message=\n%s", TSK_BUFFER_TO_STRING(buffer));
if((str = tsdp_message_tostring(message))){
TSK_DEBUG_INFO("SDP Message=\n%s", str);
TSK_FREE(str);
}
TSK_OBJECT_SAFE_FREE(buffer);
TSK_OBJECT_SAFE_FREE(message);
}
else{
@ -94,8 +97,7 @@ void test_parser()
//
// create empty message
//
if((message = tsdp_create_empty("127.0.0.1", tsk_false))){
tsk_buffer_t *buffer = TSK_BUFFER_CREATE_NULL();
if((message = tsdp_message_create_empty("127.0.0.1", tsk_false))){
/* add media */
tsdp_message_add_media(message, "audio", 8956, "RTP/AVP",
@ -126,10 +128,11 @@ void test_parser()
//tsdp_message_remove_media(message, "audio");
/* serialize the message */
tsdp_message_tostring(message, buffer);
TSK_DEBUG_INFO("\n\nEmpty SDP Message=\n%s", TSK_BUFFER_TO_STRING(buffer));
if((str = tsdp_message_tostring(message))){
TSK_DEBUG_INFO("\n\nEmpty SDP Message=\n%s", str);
TSK_FREE(str);
}
TSK_OBJECT_SAFE_FREE(buffer);
TSK_OBJECT_SAFE_FREE(message);
}
}
@ -137,9 +140,9 @@ void test_parser()
void test_caps()
{
tsdp_message_t *message = tsk_null;
char* str;
if((message = tsdp_create_empty("100.3.6.6", tsk_false))){
tsk_buffer_t *buffer = TSK_BUFFER_CREATE_NULL();
if((message = tsdp_message_create_empty("100.3.6.6", tsk_false))){
tsdp_message_add_headers(message,
TSDP_HEADER_C_VA_ARGS("IN", "IP4", "192.0.2.4"),
@ -181,12 +184,40 @@ void test_caps()
tsk_null);
/* serialize the message */
tsdp_message_tostring(message, buffer);
TSK_DEBUG_INFO("\n\nCapabilities SDP Message=\n%s", TSK_BUFFER_TO_STRING(buffer));
if((str = tsdp_message_tostring(message))){
TSK_DEBUG_INFO("\n\nCapabilities SDP Message=\n%s", str);
TSK_FREE(str);
}
TSK_OBJECT_SAFE_FREE(buffer);
TSK_OBJECT_SAFE_FREE(message);
}
}
void test_holdresume()
{
tsdp_message_t *message = tsk_null;
char* str;
if((message = tsdp_message_parse(SDP_MSG_TO_TEST, strlen(SDP_MSG_TO_TEST)))){
// hold audio
tsdp_message_hold(message, "audio");
tsdp_message_hold(message, "audio");
tsdp_message_hold(message, "video");
tsdp_message_resume(message, "video");
/* serialize the message */
if((str = tsdp_message_tostring(message))){
TSK_DEBUG_INFO("SDP Message=\n%s", str);
TSK_FREE(str);
}
TSK_OBJECT_SAFE_FREE(message);
}
else{
TSK_DEBUG_ERROR("Failed to parse SDP message.");
}
}
#endif /* _TEST_SDPPARSER_H */

View File

@ -0,0 +1,110 @@
/*
* Copyright (C) 2009 Mamadou Diop.
*
* Contact: Mamadou Diop <diopmamadou@yahoo.fr>
*
* This file is part of Open Source Doubango Framework.
*
* DOUBANGO is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* DOUBANGO is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with DOUBANGO.
*
*/
#ifndef _TEST_SOA_H
#define _TEST_SOA_H
#define SDP \
"v=0\r\n" \
"o=carol 28908764872 28908764872 IN IP4 100.3.6.6\r\n" \
"s=-\r\n" \
"t=0 0\r\n" \
"c=IN IP4 192.0.2.4\r\n" \
"m=video 0 RTP/AVP 31 34\r\n" \
"a=rtpmap:31 H261/90000\r\n" \
"a=rtpmap:34 H263/90000\r\n"
void test_create_sdp()
{
tsdp_ctx_handle_t* ctx = TSDP_CTX_CREATE();
const tsdp_message_t* sdp;
char* str;
// Create local SDP from string
tsdp_ctx_local_create_sdp_2(ctx, SDP, strlen(SDP));
if((sdp = tsdp_ctx_local_get_sdp(ctx))){
if((str = tsdp_message_tostring(sdp))){
TSK_DEBUG_INFO("Local SDP (2)=\n%s", str);
TSK_FREE(str);
}
}
// Create local SDP from object
tsdp_ctx_local_create_sdp(ctx, sdp);
if((sdp = tsdp_ctx_local_get_sdp(ctx))){
if((str = tsdp_message_tostring(sdp))){
TSK_DEBUG_INFO("Local SDP (1)=\n%s", str);
TSK_FREE(str);
}
}
// Add media to the local sdp
tsdp_ctx_local_add_media_2(ctx, "audio", 0, "RTP/AVP",
TSDP_HEADER_I_VA_ARGS("this is the (audio)information line"),
// PCMU
TSDP_FMT_VA_ARGS("0"),
TSDP_HEADER_A_VA_ARGS("rtpmap", "0 PCMU/8000"),
// 1016
TSDP_FMT_VA_ARGS("1"),
TSDP_HEADER_A_VA_ARGS("rtpmap", "1 1016/8000"),
// GSM
TSDP_FMT_VA_ARGS("3"),
TSDP_HEADER_A_VA_ARGS("rtpmap", "3 GSM/8000"),
tsk_null);
if((str = tsdp_message_tostring(sdp))){
TSK_DEBUG_INFO("Local SDP (audio)=\n%s", str);
TSK_FREE(str);
}
// Add headers to the local sdp
tsdp_ctx_local_add_headers(ctx,
TSDP_HEADER_E_VA_ARGS("j.doe@example.com (Jane Doe)"),
TSDP_HEADER_P_VA_ARGS("+44 (123)456789"),
tsk_null);
if((str = tsdp_message_tostring(sdp))){
TSK_DEBUG_INFO("Local SDP (headers)=\n%s", str);
TSK_FREE(str);
}
TSK_OBJECT_SAFE_FREE(ctx);
}
void test_soa()
{
test_create_sdp();
}
#endif /* _TEST_SOA_H */

View File

@ -33,6 +33,8 @@
#include "tinySIP_config.h"
#include "tinySIP/dialogs/tsip_dialog.h"
#include "tinySIP/media/tsip_msession.h"
#include "tsk_fsm.h"
TSIP_BEGIN_DECLS
@ -48,6 +50,8 @@ typedef struct tsip_dialog_invite
tsk_fsm_t *fsm;
uint32_t rseq;
tsip_msession_t* session; /**< Media session Manager. */
}
tsip_dialog_invite_t;

View File

@ -0,0 +1,66 @@
/*
* Copyright (C) 2009 Mamadou Diop.
*
* Contact: Mamadou Diop <diopmamadou@yahoo.fr>
*
* This file is part of Open Source Doubango Framework.
*
* DOUBANGO is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* DOUBANGO is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with DOUBANGO.
*
*/
/**@file tsip_msession.h
* @brief SIP media session.
*
* @author Mamadou Diop <diopmamadou(at)yahoo.fr>
*
* @date Created: Sat Nov 8 16:54:58 2009 mdiop
*/
#ifndef TINYSIP_MEDIA_SESSION_H
#define TINYSIP_MEDIA_SESSION_H
#include "tinySIP_config.h"
#include "tsk_object.h"
TSIP_BEGIN_DECLS
#define TSIP_MSESSION_CREATE() tsk_object_new(tsip_msession_def_t)
typedef enum tsip_msession_state_e
{
ms_none,
ms_running,
ms_paused,
ms_stopped
}
tsip_msession_state_t;
typedef struct tsip_msession_s
{
TSK_DECLARE_OBJECT;
tsip_msession_state_t state;
}
tsip_msession_t;
int tsip_msession_start(tsip_msession_t* self);
int tsip_msession_pause(tsip_msession_t* self);
int tsip_msession_stop(tsip_msession_t* self);
TINYSIP_GEXTERN const void *tsip_msession_def_t;
TSIP_END_DECLS
#endif /* TINYSIP_MEDIA_SESSION_H */

View File

@ -77,12 +77,12 @@ TSIP_BEGIN_DECLS
#define TSIP_RESPONSE_PHRASE(self) ((self)->reason_phrase)
#define TSIP_REQUEST_METHOD(self) ((self)->method)
#define TSIP_REQUEST_CSEQ_METHOD(self) ((self)->CSeq ? (self)->CSeq->method : tsk_null)
#define TSIP_REQUEST_URI(self) ((self)->uri)
#define TSIP_MESSAGE_HAS_CONTENT(message) ((message) && (message)->Content && (message)->Content->data)
#define TSIP_MESSAGE_CONTENT_LENGTH(message) (uint32_t)(((message) && (message)->Content_Length) ? (message)->Content_Length->length : 0)
#define TSIP_MESSAGE_CONTENT(message) (TSIP_MESSAGE_HAS_CONTENT(message) ? (message)->Content->data : tsk_null)
#define TSIP_MESSAGE_CSEQ_METHOD(self) ((self)->CSeq ? (self)->CSeq->method : tsk_null)
#define TSIP_MESSAGE_HAS_CONTENT(self) ((self) && (self)->Content && (self)->Content->data)
#define TSIP_MESSAGE_CONTENT_LENGTH(self) (uint32_t)(((self) && (self)->Content_Length) ? (self)->Content_Length->length : 0)
#define TSIP_MESSAGE_CONTENT(self) (TSIP_MESSAGE_HAS_CONTENT(self) ? (self)->Content->data : tsk_null)
#define TSIP_REQUEST_IS_ACK(self) ((self) &&((self)->request_type==tsip_ACK))
#define TSIP_REQUEST_IS_BYE(self) ((self) &&((self)->request_type==tsip_BYE))

View File

@ -97,7 +97,7 @@ int x9999_Any_2_Any_X_Error(va_list *app);
tsk_bool_t _fsm_cond_is_resp2INVITE(tsip_dialog_invite_t* self, tsip_message_t* message)
{
if(message->CSeq){
return tsk_striequals(message->CSeq->method, "INVITE");
return tsk_striequals(TSIP_MESSAGE_CSEQ_METHOD(message), "INVITE");
}
return tsk_false;
}
@ -412,7 +412,12 @@ int send_PRACK(tsip_dialog_invite_t *self, const tsip_response_t* r1xx)
self->rseq = RSeq->seq;
}
// Add RAck header
/* RFC 3262 - 7.2 RAck
The first number is the value from the RSeq header in the provisional
response that is being acknowledged. The next number, and the
method, are copied from the CSeq in the response that is being
acknowledged. The method name in the RAck header is case sensitive.
*/
TSIP_MESSAGE_ADD_HEADER(request, TSIP_HEADER_RACK_VA_ARGS(self->rseq, r1xx->CSeq->seq, r1xx->CSeq->method));
ret = tsip_dialog_request_send(TSIP_DIALOG(self), request);
@ -486,6 +491,8 @@ static void* tsip_dialog_invite_destroy(void * self)
/* DeInitialize base class */
tsip_dialog_deinit(TSIP_DIALOG(self));
TSK_OBJECT_SAFE_FREE(dialog->session);
}
return self;
}

View File

@ -0,0 +1,111 @@
/*
* Copyright (C) 2009 Mamadou Diop.
*
* Contact: Mamadou Diop <diopmamadou@yahoo.fr>
*
* This file is part of Open Source Doubango Framework.
*
* DOUBANGO is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* DOUBANGO is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with DOUBANGO.
*
*/
/**@file tsip_msession.c
* @brief SIP media session.
*
* @author Mamadou Diop <diopmamadou(at)yahoo.fr>
*
* @date Created: Sat Nov 8 16:54:58 2009 mdiop
*/
#include "tinySIP/media/tsip_msession.h"
int tsip_msession_start(tsip_msession_t* self)
{
int ret = -1;
if(!self){
goto bail;
}
bail:
return ret;
}
int tsip_msession_pause(tsip_msession_t* self)
{
int ret = -1;
if(!self){
goto bail;
}
bail:
return ret;
}
int tsip_msession_stop(tsip_msession_t* self)
{
int ret = -1;
if(!self){
goto bail;
}
bail:
return ret;
}
//========================================================
// SIP media session object definition
//
static tsk_object_t* tsip_msession_create(void * self, va_list * app)
{
tsip_msession_t *ms = self;
if(ms){
}
return self;
}
static tsk_object_t* tsip_msession_destroy(void * self)
{
tsip_msession_t *ms = self;
if(ms){
}
return self;
}
static const tsk_object_def_t tsip_msession_def_s =
{
sizeof(tsip_msession_t),
tsip_msession_create,
tsip_msession_destroy,
tsk_null,
};
const void *tsip_msession_def_t = &tsip_msession_def_s;

View File

@ -753,6 +753,13 @@ int tsip_transac_ict_send_ACK(tsip_transac_ict_t *self, const tsip_response_t* r
if((request = tsip_request_new("ACK", self->request->uri, self->request->From->uri, response->To->uri, self->request->Call_ID->value, self->request->CSeq->seq))){
// Via
request->firstVia = tsk_object_ref((void*)self->request->firstVia);
// tags
if(request->From){
request->From->tag = tsk_strdup(self->request->From->tag);
}
if(request->To){
request->To->tag = tsk_strdup(response->To->tag);
}
// Routes
tsk_list_foreach(item, self->request->headers){
const tsip_header_t* curr = item->data;

View File

@ -32,6 +32,15 @@
# endif
#endif
#define TEST_STACK_SDP \
"v=0\r\n" \
"o=bob 2890844730 2890844731 IN IP4 host.example.com\r\n" \
"s=\r\n" \
"c=IN IP4 192.168.0.12\r\n" \
"t=0 0\r\n" \
"m=audio 54344 RTP/AVP 0\r\n" \
"a=rtpmap:0 PCMU/8000\r\n"
#define TEST_STACK_PIDF \
"<?xml version=\"1.0\" encoding=\"utf-8\"?>"\
"<presence xmlns:cp=\"urn:ietf:params:xml:ns:pidf:cipid\" xmlns:caps=\"urn:ietf:params:xml:ns:pidf:caps\" xmlns:rpid=\"urn:ietf:params:xml:ns:pidf:rpid\" xmlns:pdm=\"urn:ietf:params:xml:ns:pidf:data-model\" xmlns:p=\"urn:ietf:params:xml:ns:pidf-diff\" xmlns:op=\"urn:oma:xml:prs:pidf:oma-pres\" entity=\"sip:mamadou@"DOMAIN"\" xmlns=\"urn:ietf:params:xml:ns:pidf\">"\
@ -226,8 +235,8 @@ int test_stack_callback(const tsip_event_t *sipevent)
void test_stack()
{
//#define DOMAIN "ericsson.com"
#define DOMAIN "micromethod.com"
#define DOMAIN "ericsson.com"
//#define DOMAIN "micromethod.com"
//#define DOMAIN "ims.inexbee.com"
//#define DOMAIN "sip2sip.info"
@ -248,7 +257,7 @@ void test_stack()
TSIP_STACK_SET_NETINFO("ADSL;utran-cell-id-3gpp=00000000"),
TSIP_STACK_SET_PRIVACY("header;id"),
*/
/*
tsip_stack_handle_t *stack = tsip_stack_create(test_stack_callback,
TSIP_STACK_SET_DISPLAY_NAME("Mamadou"),
TSIP_STACK_SET_PUBLIC_IDENTITY("sip:mamadou@"DOMAIN),
@ -258,14 +267,14 @@ void test_stack()
TSIP_STACK_SET_LOCAL_IP(LOCAL_IP),
//TSIP_STACK_SET_DISCOVERY_NAPTR(1),
TSIP_STACK_SET_PROXY_CSCF("192.168.0.14", "udp", 0),
//TSIP_STACK_SET_PROXY_CSCF("192.168.0.15", "udp", 0),
TSIP_STACK_SET_PROXY_CSCF_PORT(5081),
//TSIP_STACK_SET_PROXY_CSCF_PORT(5081),
TSIP_STACK_SET_PROXY_CSCF_PORT(5060),
//TSIP_STACK_SET_SECAGREE_IPSEC("hmac-md5-96", "null", "trans", "esp"),
TSIP_STACK_SET_MOBILITY("fixed"),
TSIP_STACK_SET_DEVICE_ID("dd1289fa-c3d7-47bd-a40d-f1f1b2cc5ffc"),
TSIP_STACK_SET_NETINFO("ADSL;utran-cell-id-3gpp=00000000"),
TSIP_STACK_SET_PRIVACY("header;id"),
*/
/*
tsip_stack_handle_t *stack = tsip_stack_create(test_stack_callback,
TSIP_STACK_SET_DISPLAY_NAME("Mamadou"),
@ -285,7 +294,7 @@ void test_stack()
TSIP_STACK_SET_NETINFO("ADSL;utran-cell-id-3gpp=00000000"),
TSIP_STACK_SET_PRIVACY("header;id"),
*/
/*
tsip_stack_handle_t *stack = tsip_stack_create(test_stack_callback,
TSIP_STACK_SET_DISPLAY_NAME("Mamadou"),
TSIP_STACK_SET_PUBLIC_IDENTITY("sip:mamadou@"DOMAIN),
@ -302,7 +311,7 @@ void test_stack()
TSIP_STACK_SET_DEVICE_ID("dd1289fa-c3d7-47bd-a40d-f1f1b2cc5ffc"),
TSIP_STACK_SET_NETINFO("ADSL;utran-cell-id-3gpp=00000000"),
TSIP_STACK_SET_PRIVACY("header;id"),
*/
TSIP_STACK_SET_NULL());
@ -330,9 +339,12 @@ void test_stack()
/* INVITE */
{
tsip_operation_handle_t *call = TSIP_OPERATION_CREATE(stack,
TSIP_OPERATION_SET_HEADER("to", "sip:bob@"DOMAIN),
TSIP_OPERATION_SET_HEADER("to", "sip:samba@"DOMAIN),
TSIP_OPERATION_SET_CAPS("+g.3gpp.icsi-ref", "\"urn%3Aurn-7%3gpp-service.ims.icsi.mmtel\""),
TSIP_OPERATION_SET_HEADER("Supported", "timer, norefersub, precondition"),
TSIP_OPERATION_SET_HEADER("Require", "100rel"),
TSIP_OPERATION_SET_PARAM("content", TEST_STACK_SDP),
TSIP_OPERATION_SET_NULL());
tsip_invite(stack, call);

View File

@ -13,6 +13,10 @@ Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tinyHTTP", "..\tinyHTTP\tin
EndProject
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tinyIPSec", "..\tinyIPSec\tinyIPSec.vcproj", "{002FF064-588F-402E-A096-C8D033F49F40}"
EndProject
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tinySDP", "..\tinySDP\tinySDP.vcproj", "{E45DB518-6562-4033-80E8-60030F0B169F}"
EndProject
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tinyMEDIA", "..\tinyMEDIA\tinyMEDIA.vcproj", "{52814B0D-7DCA-45B8-9A16-8B147040D619}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Win32 = Debug|Win32
@ -62,6 +66,18 @@ Global
{002FF064-588F-402E-A096-C8D033F49F40}.Release|Win32.ActiveCfg = Release|Win32
{002FF064-588F-402E-A096-C8D033F49F40}.Release|Win32.Build.0 = Release|Win32
{002FF064-588F-402E-A096-C8D033F49F40}.Release|Windows Mobile 5.0 Pocket PC SDK (ARMV4I).ActiveCfg = Release|Win32
{E45DB518-6562-4033-80E8-60030F0B169F}.Debug|Win32.ActiveCfg = Debug|Win32
{E45DB518-6562-4033-80E8-60030F0B169F}.Debug|Win32.Build.0 = Debug|Win32
{E45DB518-6562-4033-80E8-60030F0B169F}.Debug|Windows Mobile 5.0 Pocket PC SDK (ARMV4I).ActiveCfg = Debug|Win32
{E45DB518-6562-4033-80E8-60030F0B169F}.Release|Win32.ActiveCfg = Release|Win32
{E45DB518-6562-4033-80E8-60030F0B169F}.Release|Win32.Build.0 = Release|Win32
{E45DB518-6562-4033-80E8-60030F0B169F}.Release|Windows Mobile 5.0 Pocket PC SDK (ARMV4I).ActiveCfg = Release|Win32
{52814B0D-7DCA-45B8-9A16-8B147040D619}.Debug|Win32.ActiveCfg = Debug|Win32
{52814B0D-7DCA-45B8-9A16-8B147040D619}.Debug|Win32.Build.0 = Debug|Win32
{52814B0D-7DCA-45B8-9A16-8B147040D619}.Debug|Windows Mobile 5.0 Pocket PC SDK (ARMV4I).ActiveCfg = Debug|Win32
{52814B0D-7DCA-45B8-9A16-8B147040D619}.Release|Win32.ActiveCfg = Release|Win32
{52814B0D-7DCA-45B8-9A16-8B147040D619}.Release|Win32.Build.0 = Release|Win32
{52814B0D-7DCA-45B8-9A16-8B147040D619}.Release|Windows Mobile 5.0 Pocket PC SDK (ARMV4I).ActiveCfg = Release|Win32
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE

View File

@ -44,7 +44,7 @@
<Tool
Name="VCCLCompilerTool"
Optimization="0"
AdditionalIncludeDirectories="&quot;$(DOUBANGO_HOME)\thirdparties\win32\include&quot;;&quot;$(DOUBANGO_HOME)\tinySIP\include&quot;;&quot;$(DOUBANGO_HOME)\tinySAK\src&quot;;&quot;$(DOUBANGO_HOME)\tinyNET\src&quot;;&quot;$(DOUBANGO_HOME)\tinyHTTP\include&quot;;&quot;$(DOUBANGO_HOME)\tinyIPSec\src&quot;"
AdditionalIncludeDirectories="&quot;$(DOUBANGO_HOME)\thirdparties\win32\include&quot;;&quot;$(DOUBANGO_HOME)\tinySIP\include&quot;;&quot;$(DOUBANGO_HOME)\tinySAK\src&quot;;&quot;$(DOUBANGO_HOME)\tinyNET\src&quot;;&quot;$(DOUBANGO_HOME)\tinyHTTP\include&quot;;&quot;$(DOUBANGO_HOME)\tinyIPSec\src&quot;;&quot;$(DOUBANGO_HOME)\tinySDP\include&quot;;&quot;$(DOUBANGO_HOME)\tinyMEDIA\include&quot;"
PreprocessorDefinitions="DEBUG_LEVEL=DEBUG_LEVEL_INFO;WIN32;_DEBUG;_WINDOWS;_USRDLL;TINYSIP_EXPORTS;_WIN32_WINNT 0x0501"
MinimalRebuild="true"
RuntimeLibrary="3"
@ -65,7 +65,7 @@
/>
<Tool
Name="VCLinkerTool"
AdditionalDependencies="$(OutDir)\tinySAK.lib $(OutDir)\tinyNET.lib $(OutDir)\tinyHTTP.lib $(OutDir)\tinyIPSec.lib"
AdditionalDependencies="$(OutDir)\tinySAK.lib $(OutDir)\tinyNET.lib $(OutDir)\tinyHTTP.lib $(OutDir)\tinySDP.lib $(OutDir)\tinyMEDIA.lib $(OutDir)\tinyIPSec.lib"
LinkIncremental="2"
GenerateDebugInformation="true"
SubSystem="2"
@ -902,6 +902,14 @@
>
</File>
</Filter>
<Filter
Name="media"
>
<File
RelativePath=".\src\media\tsip_msession.c"
>
</File>
</Filter>
</Filter>
<Filter
Name="include(*.h)"
@ -1456,6 +1464,14 @@
>
</File>
</Filter>
<Filter
Name="media"
>
<File
RelativePath=".\include\tinysip\media\tsip_msession.h"
>
</File>
</Filter>
</Filter>
<Filter
Name="ragel(*.rl)"

View File

@ -139,7 +139,7 @@
<p class="body_text" align="left">
<strong>doubango</strong> is an experimental cross-platform, open source 3GPP NGN/IMS
framework for embedded systems (it also works on Windows XP/Vista/7, Mac OS X and
unix-like systems). <b>It is fully written in C</b>.
unix-like systems). It is fully written in <b>ANSI C</b>.
<br />
The framework has been carefully designed to efficiently work on embedded systems
with limited memory and low computing power and to be extremely portable.<br />