mirror of
https://gitlab.linphone.org/BC/public/linphone-iphone.git
synced 2026-05-06 21:33:08 +00:00
Merge with linphone master
This commit is contained in:
commit
3843205323
46 changed files with 1042 additions and 342 deletions
|
|
@ -61,6 +61,13 @@ endif()
|
|||
find_package(BelleSIP REQUIRED)
|
||||
find_package(MS2 REQUIRED)
|
||||
find_package(XML2 REQUIRED)
|
||||
if(ENABLE_TUNNEL)
|
||||
find_package(Tunnel)
|
||||
if(NOT TUNNEL_FOUND)
|
||||
message(WARNING "Could not find the tunnel library!")
|
||||
set(ENABLE_TUNNEL OFF CACHE BOOL "Enable tunnel support" FORCE)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
|
||||
include_directories(
|
||||
|
|
@ -72,6 +79,9 @@ include_directories(
|
|||
${MS2_INCLUDE_DIRS}
|
||||
${XML2_INCLUDE_DIRS}
|
||||
)
|
||||
if(ENABLE_TUNNEL)
|
||||
include_directories(${TUNNEL_INCLUDE_DIRS})
|
||||
endif()
|
||||
|
||||
if(MSVC)
|
||||
include_directories(${CMAKE_PREFIX_PATH}/include/MSVC)
|
||||
|
|
@ -94,6 +104,9 @@ add_definitions(-DHAVE_CONFIG_H)
|
|||
|
||||
add_subdirectory(coreapi)
|
||||
add_subdirectory(share)
|
||||
if(ENABLE_TOOLS)
|
||||
add_subdirectory(tools)
|
||||
endif()
|
||||
|
||||
|
||||
install(FILES ${CMAKE_CURRENT_SOURCE_DIR}/FindLinphone.cmake
|
||||
|
|
|
|||
|
|
@ -60,6 +60,8 @@ General rules for compilation
|
|||
- all other commands (configure, autogen.sh, make) must be done within the mingw shell (msys).
|
||||
In both msys and msys-git windows, change into the directory you created for sources:
|
||||
cd /c/sources
|
||||
- make sure pkg-config works by adding this env variable to your terminal:
|
||||
export PKG_CONFIG_PATH=/usr/lib/pkgconfig
|
||||
|
||||
Building belle-sip
|
||||
******************
|
||||
|
|
|
|||
|
|
@ -898,8 +898,8 @@ dnl ##################################################
|
|||
dnl # Check for doxygen
|
||||
dnl ##################################################
|
||||
|
||||
AC_PATH_PROG(DOXYGEN,doxygen,false)
|
||||
AM_CONDITIONAL(HAVE_DOXYGEN, test $DOXYGEN != false)
|
||||
AC_CHECK_PROG(DOXYGEN,doxygen,doxygen,false)
|
||||
AM_CONDITIONAL(HAVE_DOXYGEN, test "$DOXYGEN" != "false")
|
||||
|
||||
|
||||
AC_CONFIG_FILES([
|
||||
|
|
|
|||
|
|
@ -1601,7 +1601,7 @@ linphonec_proxy_add(LinphoneCore *lc)
|
|||
*/
|
||||
if ( enable_register==TRUE )
|
||||
{
|
||||
long int expires=0;
|
||||
int expires=0;
|
||||
while (1)
|
||||
{
|
||||
char *input=linphonec_readline("Specify register expiration time"
|
||||
|
|
@ -1613,13 +1613,8 @@ linphonec_proxy_add(LinphoneCore *lc)
|
|||
return;
|
||||
}
|
||||
|
||||
expires=strtol(input, (char **)NULL, 10);
|
||||
if ( expires == LONG_MIN || expires == LONG_MAX )
|
||||
{
|
||||
linphonec_out("Invalid value: %s\n", strerror(errno));
|
||||
free(input);
|
||||
continue;
|
||||
}
|
||||
expires=atoi(input);
|
||||
if (expires==0) expires=600;
|
||||
|
||||
linphone_proxy_config_set_expires(cfg, expires);
|
||||
linphonec_out("Expiration: %d seconds\n", linphone_proxy_config_get_expires (cfg));
|
||||
|
|
|
|||
|
|
@ -500,7 +500,6 @@ static void *pipe_thread(void*p){
|
|||
}
|
||||
|
||||
static void start_pipe_reader(void){
|
||||
ms_mutex_init(&prompt_mutex,NULL);
|
||||
pipe_reader_run=TRUE;
|
||||
ortp_thread_create(&pipe_reader_th,NULL,pipe_thread,NULL);
|
||||
}
|
||||
|
|
@ -805,6 +804,7 @@ linphonec_finish(int exit_status)
|
|||
if (mylogfile != NULL && mylogfile != stdout)
|
||||
{
|
||||
fclose (mylogfile);
|
||||
mylogfile=stdout;
|
||||
}
|
||||
printf("\n");
|
||||
exit(exit_status);
|
||||
|
|
|
|||
|
|
@ -53,7 +53,6 @@ set(SOURCE_FILES
|
|||
info.c
|
||||
linphonecall.c
|
||||
linphonecore.c
|
||||
linphone_tunnel_stubs.c
|
||||
linphone_tunnel_config.c
|
||||
lpconfig.c
|
||||
lsd.c
|
||||
|
|
@ -89,6 +88,8 @@ if(ENABLE_TUNNEL)
|
|||
TunnelManager.cc
|
||||
)
|
||||
add_definitions(-DTUNNEL_ENABLED)
|
||||
else()
|
||||
list(APPEND SOURCE_FILES linphone_tunnel_stubs.c)
|
||||
endif()
|
||||
|
||||
set(GENERATED_SOURCE_FILES
|
||||
|
|
@ -116,6 +117,9 @@ set(LIBS
|
|||
${MS2_LIBRARIES}
|
||||
${XML2_LIBRARIES}
|
||||
)
|
||||
if(ENABLE_TUNNEL)
|
||||
list(APPEND LIBS ${TUNNEL_LIBRARIES})
|
||||
endif()
|
||||
if(WIN32)
|
||||
list(APPEND LIBS shlwapi)
|
||||
endif()
|
||||
|
|
|
|||
|
|
@ -63,6 +63,7 @@ liblinphone_la_SOURCES=\
|
|||
call_log.c \
|
||||
call_params.c \
|
||||
player.c \
|
||||
fileplayer.c \
|
||||
$(GITVERSION_FILE)
|
||||
|
||||
if BUILD_UPNP
|
||||
|
|
|
|||
|
|
@ -96,6 +96,7 @@ RtpTransport *TunnelManager::createRtpTransport(int port){
|
|||
}
|
||||
|
||||
void TunnelManager::startClient() {
|
||||
ms_message("TunnelManager: Starting tunnel client");
|
||||
if (mTunnelClient == NULL) {
|
||||
mTunnelClient = new TunnelClient();
|
||||
mTunnelClient->setCallback((TunnelClientController::StateCallback)tunnelCallback,this);
|
||||
|
|
@ -111,9 +112,11 @@ void TunnelManager::startClient() {
|
|||
if(mTunnelizeSipPackets) {
|
||||
sal_enable_tunnel(mCore->sal, mTunnelClient);
|
||||
}
|
||||
mConnecting = true;
|
||||
}
|
||||
|
||||
void TunnelManager::stopClient(){
|
||||
ms_message("TunnelManager: Stopping tunnel client");
|
||||
linphone_core_set_rtp_transport_factories(mCore,NULL);
|
||||
sal_disable_tunnel(mCore->sal);
|
||||
if (mTunnelClient){
|
||||
|
|
@ -148,11 +151,12 @@ TunnelManager::TunnelManager(LinphoneCore* lc) :
|
|||
mExosipTransport(NULL),
|
||||
#endif
|
||||
mMode(LinphoneTunnelModeDisable),
|
||||
mTunnelClient(NULL),
|
||||
mIsConnected(false),
|
||||
mHttpProxyPort(0),
|
||||
mPreviousRegistrationEnabled(false),
|
||||
mAutoDetecting(false),
|
||||
mConnecting(false),
|
||||
mScheduledRegistration(false),
|
||||
mTunnelizeSipPackets(true),
|
||||
mTunnelClient(NULL),
|
||||
mHttpProxyPort(0),
|
||||
mVTable(NULL)
|
||||
{
|
||||
linphone_core_add_iterate_hook(mCore,(LinphoneCoreIterateHook)sOnIterate,this);
|
||||
|
|
@ -170,84 +174,61 @@ TunnelManager::TunnelManager(LinphoneCore* lc) :
|
|||
}
|
||||
|
||||
TunnelManager::~TunnelManager(){
|
||||
for(UdpMirrorClientList::iterator udpMirror = mUdpMirrorClients.begin(); udpMirror != mUdpMirrorClients.end(); udpMirror++) {
|
||||
udpMirror->stop();
|
||||
}
|
||||
stopClient();
|
||||
linphone_core_remove_listener(mCore, mVTable);
|
||||
linphone_vtable_destroy(mVTable);
|
||||
}
|
||||
|
||||
void TunnelManager::registration(){
|
||||
// registration occurs always after an unregistation has been made. First we
|
||||
// need to reset the previous registration mode
|
||||
LinphoneProxyConfig* lProxy;
|
||||
linphone_core_get_default_proxy(mCore, &lProxy);
|
||||
if (lProxy) {
|
||||
linphone_proxy_config_edit(lProxy);
|
||||
linphone_proxy_config_enable_register(lProxy,mPreviousRegistrationEnabled);
|
||||
linphone_proxy_config_done(lProxy);
|
||||
void TunnelManager::doRegistration(){
|
||||
if(mTunnelizeSipPackets) {
|
||||
LinphoneProxyConfig* lProxy;
|
||||
linphone_core_get_default_proxy(mCore, &lProxy);
|
||||
if (lProxy) {
|
||||
ms_message("TunnelManager: need to register");
|
||||
if(linphone_proxy_config_get_state(lProxy) != LinphoneRegistrationProgress) {
|
||||
linphone_proxy_config_refresh_register(lProxy);
|
||||
mScheduledRegistration = false;
|
||||
} else {
|
||||
ms_warning("TunnelManager: register difered. There is already a registration in progress");
|
||||
mScheduledRegistration = true;
|
||||
}
|
||||
} else {
|
||||
mScheduledRegistration = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void TunnelManager::processTunnelEvent(const Event &ev){
|
||||
if (ev.mData.mConnected){
|
||||
ms_message("Tunnel is up, registering now");
|
||||
registration();
|
||||
ms_message("Tunnel is connected");
|
||||
doRegistration();
|
||||
} else {
|
||||
ms_error("Tunnel has been disconnected");
|
||||
}
|
||||
mConnecting = false;
|
||||
}
|
||||
|
||||
void TunnelManager::waitUnRegistration() {
|
||||
LinphoneProxyConfig* lProxy;
|
||||
|
||||
linphone_core_get_default_proxy(mCore, &lProxy);
|
||||
if (lProxy){
|
||||
mPreviousRegistrationEnabled=linphone_proxy_config_register_enabled(lProxy);
|
||||
if (linphone_proxy_config_is_registered(lProxy)) {
|
||||
int i=0;
|
||||
linphone_proxy_config_edit(lProxy);
|
||||
linphone_proxy_config_enable_register(lProxy,FALSE);
|
||||
linphone_proxy_config_done(lProxy);
|
||||
sal_unregister(lProxy->op);
|
||||
//make sure unregister is sent and authenticated
|
||||
do{
|
||||
linphone_core_iterate(mCore);
|
||||
ms_usleep(20000);
|
||||
if (i>100){
|
||||
ms_message("tunnel: timeout for unregistration expired, giving up");
|
||||
break;
|
||||
}
|
||||
i++;
|
||||
}while(linphone_proxy_config_is_registered(lProxy));
|
||||
ms_message("Unregistration %s", linphone_proxy_config_is_registered(lProxy)?"failed":"succeeded");
|
||||
}else{
|
||||
ms_message("No registration pending");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*Each time tunnel is enabled/disabled, we need to unregister previous session and re-register. Since tunnel initialization
|
||||
is asynchronous, we temporary disable auto register while tunnel sets up, and reenable it when re-registering. */
|
||||
void TunnelManager::setMode(LinphoneTunnelMode mode) {
|
||||
if(mMode != mode) {
|
||||
waitUnRegistration();
|
||||
ms_message("TunnelManager: Switching mode from %s to %s",
|
||||
tunnel_mode_to_string(mMode),
|
||||
tunnel_mode_to_string(mode));
|
||||
switch(mode) {
|
||||
case LinphoneTunnelModeEnable:
|
||||
mMode = mode;
|
||||
startClient();
|
||||
/* registration is done by proccessTunnelEvent() when the tunnel
|
||||
the tunnel succeed to connect */
|
||||
break;
|
||||
case LinphoneTunnelModeDisable:
|
||||
mMode = mode;
|
||||
stopClient();
|
||||
registration();
|
||||
doRegistration();
|
||||
break;
|
||||
case LinphoneTunnelModeAuto:
|
||||
mMode = mode;
|
||||
autoDetect();
|
||||
/* Registration is not needed because processUdpMirrorEvent() will
|
||||
call either connect() or disconnect(). Should disconnect() is called,
|
||||
processUdpMirrorEvent() care to call registratin() */
|
||||
break;
|
||||
default:
|
||||
ms_error("TunnelManager::setMode(): invalid mode (%d)", mode);
|
||||
|
|
@ -263,6 +244,10 @@ void TunnelManager::tunnelCallback(bool connected, TunnelManager *zis){
|
|||
}
|
||||
|
||||
void TunnelManager::onIterate(){
|
||||
if(mScheduledRegistration) {
|
||||
ms_message("Apply difered registration");
|
||||
doRegistration();
|
||||
}
|
||||
mMutex.lock();
|
||||
while(!mEvq.empty()){
|
||||
Event ev=mEvq.front();
|
||||
|
|
@ -329,20 +314,21 @@ LinphoneTunnelMode TunnelManager::getMode() const {
|
|||
|
||||
void TunnelManager::processUdpMirrorEvent(const Event &ev){
|
||||
if (ev.mData.mHaveUdp) {
|
||||
LOGI("Tunnel is not required, disabling");
|
||||
ms_message("TunnelManager: auto detection test succeed");
|
||||
stopClient();
|
||||
registration();
|
||||
doRegistration();
|
||||
mAutoDetecting = false;
|
||||
} else {
|
||||
ms_message("TunnelManager: auto detection test failed");
|
||||
mCurrentUdpMirrorClient++;
|
||||
if (mCurrentUdpMirrorClient !=mUdpMirrorClients.end()) {
|
||||
// enable tunnel but also try backup server
|
||||
LOGI("Tunnel is required, enabling; Trying backup udp mirror");
|
||||
|
||||
ms_message("TunnelManager: trying another udp mirror");
|
||||
UdpMirrorClient &lUdpMirrorClient=*mCurrentUdpMirrorClient;
|
||||
lUdpMirrorClient.start(TunnelManager::sUdpMirrorClientCallback,(void*)this);
|
||||
} else {
|
||||
LOGI("Tunnel is required, enabling; no backup udp mirror available");
|
||||
ms_message("TunnelManager: all auto detection failed. Need ti enable tunnel");
|
||||
startClient();
|
||||
mAutoDetecting = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -369,14 +355,18 @@ void TunnelManager::networkReachableCb(LinphoneCore *lc, bool_t reachable) {
|
|||
}
|
||||
|
||||
void TunnelManager::autoDetect() {
|
||||
// first check if udp mirrors was provisionned
|
||||
if(mAutoDetecting) {
|
||||
ms_error("TunnelManager: Cannot start auto detection. One auto detection is going on");
|
||||
return;
|
||||
}
|
||||
if (mUdpMirrorClients.empty()) {
|
||||
LOGE("No UDP mirror server configured aborting auto detection");
|
||||
ms_error("TunnelManager: No UDP mirror server configured aborting auto detection");
|
||||
return;
|
||||
}
|
||||
mCurrentUdpMirrorClient = mUdpMirrorClients.begin();
|
||||
UdpMirrorClient &lUdpMirrorClient=*mCurrentUdpMirrorClient;
|
||||
lUdpMirrorClient.start(TunnelManager::sUdpMirrorClientCallback,(void*)this);
|
||||
mAutoDetecting = true;
|
||||
}
|
||||
|
||||
void TunnelManager::setHttpProxyAuthInfo(const char* username,const char* passwd) {
|
||||
|
|
@ -386,15 +376,7 @@ void TunnelManager::setHttpProxyAuthInfo(const char* username,const char* passwd
|
|||
}
|
||||
|
||||
void TunnelManager::tunnelizeSipPackets(bool enable){
|
||||
if(enable != mTunnelizeSipPackets) {
|
||||
mTunnelizeSipPackets = enable;
|
||||
if(isConnected()) {
|
||||
waitUnRegistration();
|
||||
if(mTunnelizeSipPackets) sal_enable_tunnel(mCore->sal, mTunnelClient);
|
||||
else sal_disable_tunnel(mCore->sal);
|
||||
registration();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
bool TunnelManager::tunnelizeSipPacketsEnabled() const {
|
||||
|
|
|
|||
|
|
@ -167,37 +167,37 @@ namespace belledonnecomm {
|
|||
|
||||
private:
|
||||
void onIterate();
|
||||
void registration();
|
||||
void waitUnRegistration();
|
||||
void processTunnelEvent(const Event &ev);
|
||||
void processUdpMirrorEvent(const Event &ev);
|
||||
void postEvent(const Event &ev);
|
||||
void doRegistration();
|
||||
void startClient();
|
||||
void stopClient();
|
||||
void autoDetect();
|
||||
void processTunnelEvent(const Event &ev);
|
||||
void processUdpMirrorEvent(const Event &ev);
|
||||
void postEvent(const Event &ev);
|
||||
|
||||
private:
|
||||
LinphoneCore* mCore;
|
||||
#ifndef USE_BELLESIP
|
||||
TunnelSocket *mSipSocket;
|
||||
eXosip_transport_hooks_t mExosipTransport;
|
||||
#endif
|
||||
LinphoneTunnelMode mMode;
|
||||
std::queue<Event> mEvq;
|
||||
std::list <ServerAddr> mServerAddrs;
|
||||
UdpMirrorClientList mUdpMirrorClients;
|
||||
UdpMirrorClientList::iterator mCurrentUdpMirrorClient;
|
||||
bool mAutoDetecting;
|
||||
bool mConnecting;
|
||||
bool mScheduledRegistration;
|
||||
bool mTunnelizeSipPackets;
|
||||
TunnelClient* mTunnelClient;
|
||||
Mutex mMutex;
|
||||
bool mIsConnected;
|
||||
LinphoneRtpTransportFactories mTransportFactories;
|
||||
std::string mHttpUserName;
|
||||
std::string mHttpPasswd;
|
||||
std::string mHttpProxyHost;
|
||||
int mHttpProxyPort;
|
||||
bool mPreviousRegistrationEnabled;
|
||||
bool mTunnelizeSipPackets;
|
||||
LinphoneCoreVTable *mVTable;
|
||||
std::list <ServerAddr> mServerAddrs;
|
||||
UdpMirrorClientList mUdpMirrorClients;
|
||||
UdpMirrorClientList::iterator mCurrentUdpMirrorClient;
|
||||
LinphoneRtpTransportFactories mTransportFactories;
|
||||
Mutex mMutex;
|
||||
std::queue<Event> mEvq;
|
||||
#ifndef USE_BELLESIP
|
||||
TunnelSocket *mSipSocket;
|
||||
eXosip_transport_hooks_t mExosipTransport;
|
||||
#endif
|
||||
};
|
||||
|
||||
/**
|
||||
|
|
|
|||
|
|
@ -318,6 +318,8 @@ static void call_process_transaction_terminated(void *user_ctx, const belle_sip_
|
|||
belle_sip_server_transaction_t *server_transaction=belle_sip_transaction_terminated_event_get_server_transaction(event);
|
||||
belle_sip_request_t* req;
|
||||
belle_sip_response_t* resp;
|
||||
bool_t release_call=FALSE;
|
||||
|
||||
if (client_transaction) {
|
||||
req=belle_sip_transaction_get_request(BELLE_SIP_TRANSACTION(client_transaction));
|
||||
resp=belle_sip_transaction_get_response(BELLE_SIP_TRANSACTION(client_transaction));
|
||||
|
|
@ -328,9 +330,21 @@ static void call_process_transaction_terminated(void *user_ctx, const belle_sip_
|
|||
if (op->state ==SalOpStateTerminating
|
||||
&& strcmp("BYE",belle_sip_request_get_method(req))==0
|
||||
&& (!resp || (belle_sip_response_get_status_code(resp) !=401
|
||||
&& belle_sip_response_get_status_code(resp) !=407))) {
|
||||
if (op->dialog==NULL) call_set_released(op);
|
||||
&& belle_sip_response_get_status_code(resp) !=407))
|
||||
&& op->dialog==NULL) {
|
||||
release_call=TRUE;
|
||||
}
|
||||
if (server_transaction){
|
||||
if (op->pending_server_trans==server_transaction){
|
||||
belle_sip_object_unref(op->pending_server_trans);
|
||||
op->pending_server_trans=NULL;
|
||||
}
|
||||
if (op->pending_update_server_trans==server_transaction){
|
||||
belle_sip_object_unref(op->pending_update_server_trans);
|
||||
op->pending_update_server_trans=NULL;
|
||||
}
|
||||
}
|
||||
if (release_call) call_set_released(op);
|
||||
}
|
||||
|
||||
static void call_terminated(SalOp* op,belle_sip_server_transaction_t* server_transaction, belle_sip_request_t* request,int status_code) {
|
||||
|
|
@ -777,6 +791,7 @@ int sal_call_decline(SalOp *op, SalReason reason, const char *redirection /*opti
|
|||
belle_sip_response_t* response;
|
||||
belle_sip_header_contact_t* contact=NULL;
|
||||
int status=sal_reason_to_sip_code(reason);
|
||||
belle_sip_transaction_t *trans;
|
||||
|
||||
if (reason==SalReasonRedirect){
|
||||
if (redirection!=NULL) {
|
||||
|
|
@ -788,9 +803,15 @@ int sal_call_decline(SalOp *op, SalReason reason, const char *redirection /*opti
|
|||
ms_error("Cannot redirect to null");
|
||||
}
|
||||
}
|
||||
response = sal_op_create_response_from_request(op,belle_sip_transaction_get_request(BELLE_SIP_TRANSACTION(op->pending_server_trans)),status);
|
||||
trans=(belle_sip_transaction_t*)op->pending_server_trans;
|
||||
if (!trans) trans=(belle_sip_transaction_t*)op->pending_update_server_trans;
|
||||
if (!trans){
|
||||
ms_error("sal_call_decline(): no pending transaction to decline.");
|
||||
return -1;
|
||||
}
|
||||
response = sal_op_create_response_from_request(op,belle_sip_transaction_get_request(trans),status);
|
||||
if (contact) belle_sip_message_add_header(BELLE_SIP_MESSAGE(response),BELLE_SIP_HEADER(contact));
|
||||
belle_sip_server_transaction_send_response(op->pending_server_trans,response);
|
||||
belle_sip_server_transaction_send_response(BELLE_SIP_SERVER_TRANSACTION(trans),response);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -152,7 +152,7 @@ void linphone_core_update_streams(LinphoneCore *lc, LinphoneCall *call, SalMedia
|
|||
ms_message("Network parameters have changed, update them.");
|
||||
linphone_core_update_streams_destinations(lc, call, oldmd, new_md);
|
||||
}
|
||||
if (md_changed & SAL_MEDIA_DESCRIPTION_CRYPTO_CHANGED) {
|
||||
if (md_changed & SAL_MEDIA_DESCRIPTION_CRYPTO_KEYS_CHANGED) {
|
||||
ms_message("Crypto parameters have changed, update them.");
|
||||
linphone_call_update_crypto_parameters(call, oldmd, new_md);
|
||||
}
|
||||
|
|
@ -535,7 +535,7 @@ static void call_updated_by_remote(LinphoneCore *lc, LinphoneCall *call, bool_t
|
|||
}
|
||||
if (is_update && prev_result_desc && md){
|
||||
int diff=sal_media_description_equals(prev_result_desc,md);
|
||||
if (diff & (SAL_MEDIA_DESCRIPTION_CRYPTO_CHANGED|SAL_MEDIA_DESCRIPTION_STREAMS_CHANGED)){
|
||||
if (diff & (SAL_MEDIA_DESCRIPTION_CRYPTO_POLICY_CHANGED|SAL_MEDIA_DESCRIPTION_STREAMS_CHANGED)){
|
||||
ms_warning("Cannot accept this update, it is changing parameters that require user approval");
|
||||
sal_call_decline(call->op,SalReasonNotAcceptable,NULL); /*FIXME should send 504 Cannot change the session parameters without prompting the user"*/
|
||||
return;
|
||||
|
|
@ -655,7 +655,6 @@ static void call_terminated(SalOp *op, const char *from){
|
|||
}
|
||||
|
||||
static int resume_call_after_failed_transfer(LinphoneCall *call){
|
||||
ms_message("!!!!!!!!!!resume_call_after_failed_transfer");
|
||||
if (call->was_automatically_paused && call->state==LinphoneCallPausing)
|
||||
return BELLE_SIP_CONTINUE; /*was still in pausing state*/
|
||||
|
||||
|
|
@ -663,7 +662,7 @@ static int resume_call_after_failed_transfer(LinphoneCall *call){
|
|||
if (sal_op_is_idle(call->op)){
|
||||
linphone_core_resume_call(call->core,call);
|
||||
}else {
|
||||
ms_message("!!!!!!!!!!resume_call_after_failed_transfer, salop was busy");
|
||||
ms_message("resume_call_after_failed_transfer(), salop was busy");
|
||||
return BELLE_SIP_CONTINUE;
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -424,7 +424,7 @@ LinphoneChatRoom * linphone_core_get_chat_room_from_uri(LinphoneCore *lc, const
|
|||
|
||||
static void linphone_chat_room_delete_composing_idle_timer(LinphoneChatRoom *cr) {
|
||||
if (cr->composing_idle_timer) {
|
||||
if(cr->lc->sal)
|
||||
if(cr-> lc && cr->lc->sal)
|
||||
sal_cancel_timer(cr->lc->sal, cr->composing_idle_timer);
|
||||
belle_sip_object_unref(cr->composing_idle_timer);
|
||||
cr->composing_idle_timer = NULL;
|
||||
|
|
@ -433,7 +433,7 @@ static void linphone_chat_room_delete_composing_idle_timer(LinphoneChatRoom *cr)
|
|||
|
||||
static void linphone_chat_room_delete_composing_refresh_timer(LinphoneChatRoom *cr) {
|
||||
if (cr->composing_refresh_timer) {
|
||||
if(cr->lc->sal)
|
||||
if(cr->lc && cr->lc->sal)
|
||||
sal_cancel_timer(cr->lc->sal, cr->composing_refresh_timer);
|
||||
belle_sip_object_unref(cr->composing_refresh_timer);
|
||||
cr->composing_refresh_timer = NULL;
|
||||
|
|
@ -442,7 +442,7 @@ static void linphone_chat_room_delete_composing_refresh_timer(LinphoneChatRoom *
|
|||
|
||||
static void linphone_chat_room_delete_remote_composing_refresh_timer(LinphoneChatRoom *cr) {
|
||||
if (cr->remote_composing_refresh_timer) {
|
||||
if(cr->lc->sal)
|
||||
if(cr->lc && cr->lc->sal)
|
||||
sal_cancel_timer(cr->lc->sal, cr->remote_composing_refresh_timer);
|
||||
belle_sip_object_unref(cr->remote_composing_refresh_timer);
|
||||
cr->remote_composing_refresh_timer = NULL;
|
||||
|
|
|
|||
65
coreapi/fileplayer.c
Normal file
65
coreapi/fileplayer.c
Normal file
|
|
@ -0,0 +1,65 @@
|
|||
#include "private.h"
|
||||
#include <mediastreamer2/fileplayer.h>
|
||||
#include <mediastreamer2/mssndcard.h>
|
||||
|
||||
static int file_player_open(LinphonePlayer *obj, const char *filename);
|
||||
static int file_player_start(LinphonePlayer *obj);
|
||||
static int file_player_pause(LinphonePlayer *obj);
|
||||
static int file_player_seek(LinphonePlayer *obj, int time_ms);
|
||||
static MSPlayerState file_player_get_state(LinphonePlayer *obj);
|
||||
static void file_player_close(LinphonePlayer *obj);
|
||||
static void file_player_eof_callback(void *user_data);
|
||||
|
||||
LinphonePlayer *linphone_core_create_file_player(LinphoneCore *lc, MSSndCard *snd_card, const char *video_out) {
|
||||
LinphonePlayer *obj = ms_new0(LinphonePlayer, 1);
|
||||
if(snd_card == NULL) snd_card = lc->sound_conf.play_sndcard;
|
||||
if(video_out == NULL) video_out = linphone_core_get_video_display_filter(lc);
|
||||
obj->impl = ms_file_player_new(snd_card, video_out);
|
||||
obj->open = file_player_open;
|
||||
obj->start = file_player_start;
|
||||
obj->pause = file_player_pause;
|
||||
obj->seek = file_player_seek;
|
||||
obj->get_state = file_player_get_state;
|
||||
obj->close = file_player_close;
|
||||
ms_file_player_set_eof_callback((MSFilePlayer *)obj->impl, file_player_eof_callback, obj);
|
||||
return obj;
|
||||
}
|
||||
|
||||
void linphone_file_player_destroy(LinphonePlayer *obj) {
|
||||
ms_file_player_free((MSFilePlayer *)obj->impl);
|
||||
ms_free(obj);
|
||||
}
|
||||
|
||||
bool_t linphone_file_player_matroska_supported(void) {
|
||||
return ms_file_player_matroska_supported();
|
||||
}
|
||||
|
||||
static int file_player_open(LinphonePlayer *obj, const char *filename) {
|
||||
return ms_file_player_open((MSFilePlayer *)obj->impl, filename) ? 0 : -1;
|
||||
}
|
||||
|
||||
static int file_player_start(LinphonePlayer *obj) {
|
||||
return ms_file_player_start((MSFilePlayer *)obj->impl) ? 0 : -1;
|
||||
}
|
||||
|
||||
static int file_player_pause(LinphonePlayer *obj) {
|
||||
ms_file_player_pause((MSFilePlayer *)obj->impl);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int file_player_seek(LinphonePlayer *obj, int time_ms) {
|
||||
return ms_file_player_seek((MSFilePlayer *)obj->impl, time_ms) ? 0 : -1;
|
||||
}
|
||||
|
||||
static MSPlayerState file_player_get_state(LinphonePlayer *obj) {
|
||||
return ms_file_player_get_state((MSFilePlayer *)obj->impl);
|
||||
}
|
||||
|
||||
static void file_player_close(LinphonePlayer *obj) {
|
||||
ms_file_player_close((MSFilePlayer *)obj->impl);
|
||||
}
|
||||
|
||||
static void file_player_eof_callback(void *user_data) {
|
||||
LinphonePlayer *obj = (LinphonePlayer *)user_data;
|
||||
obj->cb(obj, obj->user_data);
|
||||
}
|
||||
|
|
@ -31,9 +31,6 @@
|
|||
|
||||
static const char *_tunnel_mode_str[3] = { "disable", "enable", "auto" };
|
||||
|
||||
static LinphoneTunnelMode _string_to_tunnel_mode(const char *string);
|
||||
static const char *_tunnel_mode_to_string(LinphoneTunnelMode mode);
|
||||
|
||||
LinphoneTunnel* linphone_core_get_tunnel(const LinphoneCore *lc){
|
||||
return lc->tunnel;
|
||||
}
|
||||
|
|
@ -237,7 +234,7 @@ void linphone_tunnel_clean_servers(LinphoneTunnel *tunnel){
|
|||
}
|
||||
|
||||
void linphone_tunnel_set_mode(LinphoneTunnel *tunnel, LinphoneTunnelMode mode){
|
||||
lp_config_set_string(config(tunnel),"tunnel","mode", _tunnel_mode_to_string(mode));
|
||||
lp_config_set_string(config(tunnel),"tunnel","mode", tunnel_mode_to_string(mode));
|
||||
bcTunnel(tunnel)->setMode(mode);
|
||||
}
|
||||
|
||||
|
|
@ -335,7 +332,7 @@ static void my_ortp_logv(OrtpLogLevel level, const char *fmt, va_list args){
|
|||
ortp_logv(level,fmt,args);
|
||||
}
|
||||
|
||||
static LinphoneTunnelMode _string_to_tunnel_mode(const char *string) {
|
||||
LinphoneTunnelMode string_to_tunnel_mode(const char *string) {
|
||||
if(string != NULL) {
|
||||
int i;
|
||||
for(i=0; i<3 && strcmp(string, _tunnel_mode_str[i]) != 0; i++);
|
||||
|
|
@ -350,7 +347,7 @@ static LinphoneTunnelMode _string_to_tunnel_mode(const char *string) {
|
|||
}
|
||||
}
|
||||
|
||||
static const char *_tunnel_mode_to_string(LinphoneTunnelMode mode) {
|
||||
const char *tunnel_mode_to_string(LinphoneTunnelMode mode) {
|
||||
return _tunnel_mode_str[mode];
|
||||
}
|
||||
|
||||
|
|
@ -359,7 +356,7 @@ static const char *_tunnel_mode_to_string(LinphoneTunnelMode mode) {
|
|||
* Called internally from linphonecore at startup.
|
||||
*/
|
||||
void linphone_tunnel_configure(LinphoneTunnel *tunnel){
|
||||
LinphoneTunnelMode mode = _string_to_tunnel_mode(lp_config_get_string(config(tunnel), "tunnel", "mode", NULL));
|
||||
LinphoneTunnelMode mode = string_to_tunnel_mode(lp_config_get_string(config(tunnel), "tunnel", "mode", NULL));
|
||||
bool_t tunnelizeSIPPackets = (bool_t)lp_config_get_int(config(tunnel), "tunnel", "sip", TRUE);
|
||||
linphone_tunnel_enable_logs_with_handler(tunnel,TRUE,my_ortp_logv);
|
||||
linphone_tunnel_load_config(tunnel);
|
||||
|
|
|
|||
|
|
@ -50,12 +50,30 @@ extern "C"
|
|||
|
||||
typedef struct _LinphoneTunnelConfig LinphoneTunnelConfig;
|
||||
|
||||
/**
|
||||
* Enum describing the tunnel modes.
|
||||
**/
|
||||
typedef enum _LinphoneTunnelMode {
|
||||
LinphoneTunnelModeDisable,
|
||||
LinphoneTunnelModeEnable,
|
||||
LinphoneTunnelModeAuto
|
||||
LinphoneTunnelModeDisable, /**< The tunnel is disabled. */
|
||||
LinphoneTunnelModeEnable, /**< The tunnel is enabled. */
|
||||
LinphoneTunnelModeAuto /**< The tunnel is enabled automatically if it is required. */
|
||||
} LinphoneTunnelMode;
|
||||
|
||||
/**
|
||||
* @brief Convert a string into LinphoneTunnelMode enum
|
||||
* @param string String to convert
|
||||
* @return An LinphoneTunnelMode enum. If the passed string is NULL or
|
||||
* does not match with any mode, the LinphoneTunnelModeDisable is returned.
|
||||
*/
|
||||
LINPHONE_PUBLIC LinphoneTunnelMode string_to_tunnel_mode(const char *string);
|
||||
|
||||
/**
|
||||
* @brief Convert a tunnel mode enum into string
|
||||
* @param mode Enum to convert
|
||||
* @return "disable", "enable" or "auto"
|
||||
*/
|
||||
LINPHONE_PUBLIC const char *tunnel_mode_to_string(LinphoneTunnelMode mode);
|
||||
|
||||
/**
|
||||
* Create a new tunnel configuration
|
||||
*/
|
||||
|
|
@ -268,7 +286,6 @@ LINPHONE_PUBLIC void linphone_tunnel_auto_detect(LinphoneTunnel *tunnel);
|
|||
*/
|
||||
LINPHONE_PUBLIC bool_t linphone_tunnel_auto_detect_enabled(LinphoneTunnel *tunnel);
|
||||
|
||||
|
||||
/**
|
||||
* @}
|
||||
**/
|
||||
|
|
|
|||
|
|
@ -1662,6 +1662,19 @@ static void parametrize_equalizer(LinphoneCore *lc, AudioStream *st){
|
|||
}
|
||||
}
|
||||
|
||||
void set_mic_gain_db(AudioStream *st, float gain){
|
||||
if (st->volsend){
|
||||
ms_filter_call_method(st->volsend,MS_VOLUME_SET_DB_GAIN,&gain);
|
||||
}else ms_warning("Could not apply mic gain: gain control wasn't activated.");
|
||||
}
|
||||
|
||||
void set_playback_gain_db(AudioStream *st, float gain){
|
||||
if (st->volrecv){
|
||||
ms_filter_call_method(st->volrecv,MS_VOLUME_SET_DB_GAIN,&gain);
|
||||
}else ms_warning("Could not apply playback gain: gain control wasn't activated.");
|
||||
}
|
||||
|
||||
/*This function is not static because used internally in linphone-daemon project*/
|
||||
void _post_configure_audio_stream(AudioStream *st, LinphoneCore *lc, bool_t muted){
|
||||
float mic_gain=lc->sound_conf.soft_mic_lev;
|
||||
float thres = 0;
|
||||
|
|
@ -1678,13 +1691,13 @@ void _post_configure_audio_stream(AudioStream *st, LinphoneCore *lc, bool_t mute
|
|||
int spk_agc;
|
||||
|
||||
if (!muted)
|
||||
linphone_core_set_mic_gain_db (lc, mic_gain);
|
||||
set_mic_gain_db(st,mic_gain);
|
||||
else
|
||||
audio_stream_set_mic_gain(st,0);
|
||||
|
||||
recv_gain = lc->sound_conf.soft_play_lev;
|
||||
if (recv_gain != 0) {
|
||||
linphone_core_set_playback_gain_db (lc,recv_gain);
|
||||
set_playback_gain_db(st,recv_gain);
|
||||
}
|
||||
|
||||
if (st->volsend){
|
||||
|
|
@ -1720,10 +1733,10 @@ void _post_configure_audio_stream(AudioStream *st, LinphoneCore *lc, bool_t mute
|
|||
parametrize_equalizer(lc,st);
|
||||
}
|
||||
|
||||
static void post_configure_audio_streams(LinphoneCall*call){
|
||||
static void post_configure_audio_streams(LinphoneCall *call, bool_t muted){
|
||||
AudioStream *st=call->audiostream;
|
||||
LinphoneCore *lc=call->core;
|
||||
_post_configure_audio_stream(st,lc,call->audio_muted);
|
||||
_post_configure_audio_stream(st,lc,muted);
|
||||
if (linphone_core_dtmf_received_has_listener(lc)){
|
||||
audio_stream_play_received_dtmfs(call->audiostream,FALSE);
|
||||
}
|
||||
|
|
@ -1996,10 +2009,7 @@ static void linphone_call_start_audio_stream(LinphoneCall *call, const char *cna
|
|||
captcard,
|
||||
use_ec
|
||||
);
|
||||
post_configure_audio_streams(call);
|
||||
if (muted && !send_ringbacktone){
|
||||
audio_stream_set_mic_gain(call->audiostream,0);
|
||||
}
|
||||
post_configure_audio_streams(call, muted && !send_ringbacktone);
|
||||
if (stream->dir==SalStreamSendOnly && playfile!=NULL){
|
||||
int pause_time=500;
|
||||
ms_filter_call_method(call->audiostream->soundread,MS_FILE_PLAYER_LOOP,&pause_time);
|
||||
|
|
@ -2220,7 +2230,7 @@ void linphone_call_stop_media_streams_for_ice_gathering(LinphoneCall *call){
|
|||
static bool_t update_stream_crypto_params(LinphoneCall *call, const SalStreamDescription *local_st_desc, SalStreamDescription *old_stream, SalStreamDescription *new_stream, MediaStream *ms){
|
||||
int crypto_idx = find_crypto_index_from_tag(local_st_desc->crypto, new_stream->crypto_local_tag);
|
||||
if (crypto_idx >= 0) {
|
||||
if (call->localdesc_changed & SAL_MEDIA_DESCRIPTION_CRYPTO_CHANGED)
|
||||
if (call->localdesc_changed & SAL_MEDIA_DESCRIPTION_CRYPTO_KEYS_CHANGED)
|
||||
media_stream_set_srtp_send_key(ms,new_stream->crypto[0].algo,local_st_desc->crypto[crypto_idx].master_key);
|
||||
if (strcmp(old_stream->crypto[0].master_key,new_stream->crypto[0].master_key)!=0){
|
||||
media_stream_set_srtp_recv_key(ms,new_stream->crypto[0].algo,new_stream->crypto[0].master_key);
|
||||
|
|
@ -2634,10 +2644,10 @@ uint64_t linphone_call_stats_get_late_packets_cumulative_number(const LinphoneCa
|
|||
if (!stats || !call)
|
||||
return 0;
|
||||
memset(&rtp_stats, 0, sizeof(rtp_stats));
|
||||
if (stats->type == LINPHONE_CALL_STATS_AUDIO)
|
||||
if (stats->type == LINPHONE_CALL_STATS_AUDIO && call->audiostream != NULL)
|
||||
audio_stream_get_local_rtp_stats(call->audiostream, &rtp_stats);
|
||||
#ifdef VIDEO_ENABLED
|
||||
else
|
||||
else if (call->videostream != NULL)
|
||||
video_stream_get_local_rtp_stats(call->videostream, &rtp_stats);
|
||||
#endif
|
||||
return rtp_stats.outoftime;
|
||||
|
|
|
|||
|
|
@ -1630,8 +1630,7 @@ void linphone_core_set_use_rfc2833_for_dtmf(LinphoneCore *lc,bool_t use_rfc2833)
|
|||
* Deprecated: use linphone_core_get_sip_transports() instead.
|
||||
* @ingroup network_parameters
|
||||
**/
|
||||
int linphone_core_get_sip_port(LinphoneCore *lc)
|
||||
{
|
||||
int linphone_core_get_sip_port(LinphoneCore *lc){
|
||||
LCSipTransports tr;
|
||||
linphone_core_get_sip_transports_used(lc,&tr);
|
||||
return tr.udp_port>0 ? tr.udp_port : (tr.tcp_port > 0 ? tr.tcp_port : tr.tls_port);
|
||||
|
|
@ -2857,6 +2856,7 @@ int linphone_core_accept_early_media(LinphoneCore* lc, LinphoneCall* call){
|
|||
|
||||
int linphone_core_start_update_call(LinphoneCore *lc, LinphoneCall *call){
|
||||
const char *subject;
|
||||
int err;
|
||||
bool_t no_user_consent=call->params->no_user_consent;
|
||||
|
||||
if (!no_user_consent) linphone_call_make_local_media_description(lc,call);
|
||||
|
|
@ -2873,12 +2873,22 @@ int linphone_core_start_update_call(LinphoneCore *lc, LinphoneCall *call){
|
|||
subject="Refreshing";
|
||||
}
|
||||
linphone_core_notify_display_status(lc,_("Modifying call parameters..."));
|
||||
sal_call_set_local_media_description (call->op,call->localdesc);
|
||||
if (!lc->sip_conf.sdp_200_ack){
|
||||
sal_call_set_local_media_description (call->op,call->localdesc);
|
||||
} else {
|
||||
sal_call_set_local_media_description (call->op,NULL);
|
||||
}
|
||||
if (call->dest_proxy && call->dest_proxy->op){
|
||||
/*give a chance to update the contact address if connectivity has changed*/
|
||||
sal_op_set_contact_address(call->op,sal_op_get_contact_address(call->dest_proxy->op));
|
||||
}else sal_op_set_contact_address(call->op,NULL);
|
||||
return sal_call_update(call->op,subject,no_user_consent);
|
||||
err= sal_call_update(call->op,subject,no_user_consent);
|
||||
if (lc->sip_conf.sdp_200_ack){
|
||||
/*we are NOT offering, set local media description after sending the call so that we are ready to
|
||||
process the remote offer when it will arrive*/
|
||||
sal_call_set_local_media_description(call->op,call->localdesc);
|
||||
}
|
||||
return err;
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
@ -3789,9 +3799,7 @@ void linphone_core_set_mic_gain_db (LinphoneCore *lc, float gaindb){
|
|||
ms_message("linphone_core_set_mic_gain_db(): no active call.");
|
||||
return;
|
||||
}
|
||||
if (st->volsend){
|
||||
ms_filter_call_method(st->volsend,MS_VOLUME_SET_DB_GAIN,&gain);
|
||||
}else ms_warning("Could not apply gain: gain control wasn't activated.");
|
||||
set_mic_gain_db(st,gain);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
@ -3822,9 +3830,7 @@ void linphone_core_set_playback_gain_db (LinphoneCore *lc, float gaindb){
|
|||
ms_message("linphone_core_set_playback_gain_db(): no active call.");
|
||||
return;
|
||||
}
|
||||
if (st->volrecv){
|
||||
ms_filter_call_method(st->volrecv,MS_VOLUME_SET_DB_GAIN,&gain);
|
||||
}else ms_warning("Could not apply gain: gain control wasn't activated.");
|
||||
set_playback_gain_db(st,gain);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
@ -4467,11 +4473,11 @@ void linphone_core_set_firewall_policy(LinphoneCore *lc, LinphoneFirewallPolicy
|
|||
lp_config_set_string(lc->config,"net","firewall_policy",policy);
|
||||
}
|
||||
|
||||
inline LinphoneFirewallPolicy linphone_core_get_firewall_policy(const LinphoneCore *lc) {
|
||||
ORTP_INLINE LinphoneFirewallPolicy linphone_core_get_firewall_policy(const LinphoneCore *lc) {
|
||||
return _linphone_core_get_firewall_policy_with_lie(lc, FALSE);
|
||||
}
|
||||
|
||||
inline LinphoneFirewallPolicy _linphone_core_get_firewall_policy(const LinphoneCore *lc) {
|
||||
ORTP_INLINE LinphoneFirewallPolicy _linphone_core_get_firewall_policy(const LinphoneCore *lc) {
|
||||
return _linphone_core_get_firewall_policy_with_lie(lc, TRUE);
|
||||
}
|
||||
|
||||
|
|
@ -5003,15 +5009,15 @@ int linphone_core_get_camera_sensor_rotation(LinphoneCore *lc) {
|
|||
}
|
||||
|
||||
static MSVideoSizeDef supported_resolutions[]={
|
||||
#if !ANDROID & !TARGET_OS_IPHONE
|
||||
#if !ANDROID && !TARGET_OS_IPHONE
|
||||
{ { MS_VIDEO_SIZE_1080P_W, MS_VIDEO_SIZE_1080P_H } , "1080p" },
|
||||
#endif
|
||||
#if !ANDROID & !TARGET_OS_MAC /*limite to most common size because mac card cannot list supported resolutions*/
|
||||
#if !ANDROID && !TARGET_OS_MAC /*limit to most common sizes because mac video API cannot list supported resolutions*/
|
||||
{ { MS_VIDEO_SIZE_UXGA_W, MS_VIDEO_SIZE_UXGA_H } , "uxga" },
|
||||
{ { MS_VIDEO_SIZE_SXGA_MINUS_W, MS_VIDEO_SIZE_SXGA_MINUS_H } , "sxga-" },
|
||||
#endif
|
||||
{ { MS_VIDEO_SIZE_720P_W, MS_VIDEO_SIZE_720P_H } , "720p" },
|
||||
#if !ANDROID & !TARGET_OS_MAC
|
||||
#if !ANDROID && !TARGET_OS_MAC
|
||||
{ { MS_VIDEO_SIZE_XGA_W, MS_VIDEO_SIZE_XGA_H } , "xga" },
|
||||
#endif
|
||||
#if !ANDROID && !TARGET_OS_IPHONE
|
||||
|
|
@ -5043,23 +5049,33 @@ const MSVideoSizeDef *linphone_core_get_supported_video_sizes(LinphoneCore *lc){
|
|||
static MSVideoSize video_size_get_by_name(const char *name){
|
||||
MSVideoSizeDef *pdef=supported_resolutions;
|
||||
MSVideoSize null_vsize={0,0};
|
||||
MSVideoSize parsed;
|
||||
if (!name) return null_vsize;
|
||||
for(;pdef->name!=NULL;pdef++){
|
||||
if (strcasecmp(name,pdef->name)==0){
|
||||
return pdef->vsize;
|
||||
}
|
||||
}
|
||||
if (sscanf(name,"%ix%i",&parsed.width,&parsed.height)==2){
|
||||
return parsed;
|
||||
}
|
||||
ms_warning("Video resolution %s is not supported in linphone.",name);
|
||||
return null_vsize;
|
||||
}
|
||||
|
||||
/* warning: function not reentrant*/
|
||||
static const char *video_size_get_name(MSVideoSize vsize){
|
||||
MSVideoSizeDef *pdef=supported_resolutions;
|
||||
static char customsize[64]={0};
|
||||
for(;pdef->name!=NULL;pdef++){
|
||||
if (pdef->vsize.width==vsize.width && pdef->vsize.height==vsize.height){
|
||||
return pdef->name;
|
||||
}
|
||||
}
|
||||
if (vsize.width && vsize.height){
|
||||
snprintf(customsize,sizeof(customsize)-1,"%ix%i",vsize.width,vsize.height);
|
||||
return customsize;
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
|
@ -5108,6 +5124,7 @@ void linphone_core_set_preferred_video_size(LinphoneCore *lc, MSVideoSize vsize)
|
|||
* @param vsize the video resolution choosed for capuring and previewing. It can be (0,0) to not request any specific preview size and let the core optimize the processing.
|
||||
**/
|
||||
void linphone_core_set_preview_video_size(LinphoneCore *lc, MSVideoSize vsize){
|
||||
MSVideoSize oldvsize;
|
||||
if (vsize.width==0 && vsize.height==0){
|
||||
/*special case to reset the forced preview size mode*/
|
||||
lc->video_conf.preview_vsize=vsize;
|
||||
|
|
@ -5115,16 +5132,25 @@ void linphone_core_set_preview_video_size(LinphoneCore *lc, MSVideoSize vsize){
|
|||
lp_config_set_string(lc->config,"video","preview_size",NULL);
|
||||
return;
|
||||
}
|
||||
if (video_size_supported(vsize)){
|
||||
MSVideoSize oldvsize=lc->video_conf.preview_vsize;
|
||||
lc->video_conf.preview_vsize=vsize;
|
||||
if (!ms_video_size_equal(oldvsize,vsize) && lc->previewstream!=NULL){
|
||||
toggle_video_preview(lc,FALSE);
|
||||
toggle_video_preview(lc,TRUE);
|
||||
}
|
||||
if (linphone_core_ready(lc))
|
||||
lp_config_set_string(lc->config,"video","preview_size",video_size_get_name(vsize));
|
||||
oldvsize=lc->video_conf.preview_vsize;
|
||||
lc->video_conf.preview_vsize=vsize;
|
||||
if (!ms_video_size_equal(oldvsize,vsize) && lc->previewstream!=NULL){
|
||||
toggle_video_preview(lc,FALSE);
|
||||
toggle_video_preview(lc,TRUE);
|
||||
}
|
||||
if (linphone_core_ready(lc))
|
||||
lp_config_set_string(lc->config,"video","preview_size",video_size_get_name(vsize));
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns video size for the captured video if it was previously set by linphone_core_set_preview_video_size(), otherwise returns a 0,0 size.
|
||||
* @see linphone_core_set_preview_video_size()
|
||||
* @ingroup media_parameters
|
||||
* @param lc the core
|
||||
* @return a MSVideoSize
|
||||
**/
|
||||
MSVideoSize linphone_core_get_preview_video_size(const LinphoneCore *lc){
|
||||
return lc->video_conf.preview_vsize;
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
|||
|
|
@ -596,6 +596,28 @@ int linphone_player_seek(LinphonePlayer *obj, int time_ms);
|
|||
MSPlayerState linphone_player_get_state(LinphonePlayer *obj);
|
||||
void linphone_player_close(LinphonePlayer *obj);
|
||||
|
||||
/**
|
||||
* @brief Create an independent media file player.
|
||||
* This player support WAVE and MATROSKA formats.
|
||||
* @param lc A LinphoneCore
|
||||
* @param snd_card Playback sound card. If NULL, the sound card set in LinphoneCore will be used
|
||||
* @param video_out Video display. If NULL, the video display set in LinphoneCore will be used
|
||||
* @return A pointer on the new instance. NULL if faild.
|
||||
*/
|
||||
LINPHONE_PUBLIC LinphonePlayer *linphone_core_create_file_player(LinphoneCore *lc, MSSndCard *snd_card, const char *video_out);
|
||||
|
||||
/**
|
||||
* @brief Destroy a file player
|
||||
* @param obj File player to destroy
|
||||
*/
|
||||
LINPHONE_PUBLIC void linphone_file_player_destroy(LinphonePlayer *obj);
|
||||
|
||||
/**
|
||||
* @brief Check whether Matroksa format is supported by the player
|
||||
* @return TRUE if it is supported
|
||||
*/
|
||||
LINPHONE_PUBLIC bool_t linphone_file_player_matroska_supported(void);
|
||||
|
||||
/**
|
||||
* LinphoneCallState enum represents the different state a call can reach into.
|
||||
* The application is notified of state changes through the LinphoneCoreVTable::call_state_changed callback.
|
||||
|
|
@ -2536,6 +2558,7 @@ LINPHONE_PUBLIC const MSVideoSizeDef *linphone_core_get_supported_video_sizes(Li
|
|||
LINPHONE_PUBLIC void linphone_core_set_preferred_video_size(LinphoneCore *lc, MSVideoSize vsize);
|
||||
LINPHONE_PUBLIC void linphone_core_set_preview_video_size(LinphoneCore *lc, MSVideoSize vsize);
|
||||
LINPHONE_PUBLIC void linphone_core_set_preview_video_size_by_name(LinphoneCore *lc, const char *name);
|
||||
LINPHONE_PUBLIC MSVideoSize linphone_core_get_preview_video_size(const LinphoneCore *lc);
|
||||
LINPHONE_PUBLIC MSVideoSize linphone_core_get_preferred_video_size(LinphoneCore *lc);
|
||||
LINPHONE_PUBLIC void linphone_core_set_preferred_video_size_by_name(LinphoneCore *lc, const char *name);
|
||||
LINPHONE_PUBLIC void linphone_core_set_preferred_framerate(LinphoneCore *lc, float fps);
|
||||
|
|
|
|||
|
|
@ -40,7 +40,11 @@
|
|||
#endif /*_WIN32_WCE*/
|
||||
|
||||
#ifdef _MSC_VER
|
||||
#ifdef WINAPI_FAMILY_PHONE_APP
|
||||
#include <stdlib.h>
|
||||
#else
|
||||
#include <Shlwapi.h>
|
||||
#endif
|
||||
#else
|
||||
#include <libgen.h>
|
||||
#endif
|
||||
|
|
@ -666,9 +670,18 @@ const char* lp_config_get_default_string(const LpConfig *lpconfig, const char *s
|
|||
|
||||
static char *_lp_config_dirname(char *path) {
|
||||
#ifdef _MSC_VER
|
||||
#ifdef WINAPI_FAMILY_PHONE_APP
|
||||
char drive[_MAX_DRIVE];
|
||||
char dir[_MAX_DIR];
|
||||
char fname[_MAX_FNAME];
|
||||
char ext[_MAX_EXT];
|
||||
_splitpath(path, drive, dir, fname, ext);
|
||||
return ms_strdup_printf("%s%s", drive, dir);
|
||||
#else
|
||||
char *dir = ms_strdup(path);
|
||||
PathRemoveFileSpec(dir);
|
||||
return dir;
|
||||
#endif
|
||||
#else
|
||||
char *tmp = ms_strdup(path);
|
||||
char *dir = ms_strdup(dirname(tmp));
|
||||
|
|
|
|||
|
|
@ -937,7 +937,7 @@ void linphone_core_update_ice_from_remote_media_description(LinphoneCall *call,
|
|||
bool_t linphone_core_media_description_contains_video_stream(const SalMediaDescription *md){
|
||||
int i;
|
||||
|
||||
for (i = 0; i < md->nb_streams; i++) {
|
||||
for (i = 0; md && i < md->nb_streams; i++) {
|
||||
if (md->streams[i].type == SalVideo && md->streams[i].rtp_port!=0)
|
||||
return TRUE;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -31,7 +31,7 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|||
int linphone_player_open(LinphonePlayer *obj, const char *filename, LinphonePlayerEofCallback cb, void *user_data){
|
||||
obj->user_data=user_data;
|
||||
obj->cb=cb;
|
||||
return obj->open(obj->impl,filename);
|
||||
return obj->open(obj,filename);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
@ -40,7 +40,7 @@ int linphone_player_open(LinphonePlayer *obj, const char *filename, LinphonePlay
|
|||
* @return 0 if successful, -1 otherwise
|
||||
**/
|
||||
int linphone_player_start(LinphonePlayer *obj){
|
||||
return obj->start(obj->impl);
|
||||
return obj->start(obj);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
@ -49,7 +49,7 @@ int linphone_player_start(LinphonePlayer *obj){
|
|||
* @return 0 if successful, -1 otherwise
|
||||
**/
|
||||
int linphone_player_pause(LinphonePlayer *obj){
|
||||
return obj->pause(obj->impl);
|
||||
return obj->pause(obj);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
@ -59,7 +59,7 @@ int linphone_player_pause(LinphonePlayer *obj){
|
|||
* @return 0 if successful, -1 otherwise
|
||||
**/
|
||||
int linphone_player_seek(LinphonePlayer *obj, int time_ms){
|
||||
return obj->seek(obj->impl,time_ms);
|
||||
return obj->seek(obj,time_ms);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
@ -68,7 +68,7 @@ int linphone_player_seek(LinphonePlayer *obj, int time_ms){
|
|||
* @return the state of the player within MSPlayerClosed, MSPlayerStarted, MSPlayerPaused.
|
||||
**/
|
||||
MSPlayerState linphone_player_get_state(LinphonePlayer *obj){
|
||||
return obj->get_state(obj->impl);
|
||||
return obj->get_state(obj);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
@ -76,7 +76,7 @@ MSPlayerState linphone_player_get_state(LinphonePlayer *obj){
|
|||
* @param obj the player.
|
||||
**/
|
||||
void linphone_player_close(LinphonePlayer *obj){
|
||||
return obj->close(obj->impl);
|
||||
return obj->close(obj);
|
||||
}
|
||||
|
||||
|
||||
|
|
@ -104,7 +104,7 @@ static bool_t call_player_check_state(LinphonePlayer *player, bool_t check_playe
|
|||
|
||||
static void on_eof(void *user_data, MSFilter *f, unsigned int event_id, void *arg){
|
||||
LinphonePlayer *player=(LinphonePlayer *)user_data;
|
||||
if (player->cb) player->cb(player,user_data);
|
||||
if (player->cb) player->cb(player,player->user_data);
|
||||
}
|
||||
|
||||
static int call_player_open(LinphonePlayer* player, const char *filename){
|
||||
|
|
@ -146,7 +146,7 @@ static int call_player_seek(LinphonePlayer *player, int time_ms){
|
|||
static void call_player_close(LinphonePlayer *player){
|
||||
LinphoneCall *call=(LinphoneCall*)player->impl;
|
||||
if (!call_player_check_state(player,TRUE)) return;
|
||||
ms_filter_call_method_noarg(call->audiostream->av_player.player,MS_PLAYER_CLOSE);
|
||||
audio_stream_close_remote_play(call->audiostream);
|
||||
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -1021,7 +1021,8 @@ void linphone_core_notify_notify_received(LinphoneCore *lc, LinphoneEvent *lev,
|
|||
void linphone_core_notify_subscription_state_changed(LinphoneCore *lc, LinphoneEvent *lev, LinphoneSubscriptionState state);
|
||||
void linphone_core_notify_publish_state_changed(LinphoneCore *lc, LinphoneEvent *lev, LinphonePublishState state);
|
||||
|
||||
|
||||
void set_mic_gain_db(AudioStream *st, float gain);
|
||||
void set_playback_gain_db(AudioStream *st, float gain);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1408,12 +1408,7 @@ static bool_t can_register(LinphoneProxyConfig *cfg){
|
|||
}
|
||||
#endif //BUILD_UPNP
|
||||
if (lc->sip_conf.register_only_when_network_is_up){
|
||||
LinphoneTunnel *tunnel=linphone_core_get_tunnel(lc);
|
||||
if (tunnel && linphone_tunnel_get_mode(tunnel)){
|
||||
return linphone_tunnel_connected(tunnel);
|
||||
}else{
|
||||
return lc->network_reachable;
|
||||
}
|
||||
return lc->network_reachable;
|
||||
}
|
||||
return TRUE;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -280,9 +280,11 @@ int sal_stream_description_equals(const SalStreamDescription *sd1, const SalStre
|
|||
if (sd1->proto != sd2->proto) result |= SAL_MEDIA_DESCRIPTION_CODEC_CHANGED;
|
||||
for (i = 0; i < SAL_CRYPTO_ALGO_MAX; i++) {
|
||||
if ((sd1->crypto[i].tag != sd2->crypto[i].tag)
|
||||
|| (sd1->crypto[i].algo != sd2->crypto[i].algo)
|
||||
|| (strncmp(sd1->crypto[i].master_key, sd2->crypto[i].master_key, sizeof(sd1->crypto[i].master_key) - 1))) {
|
||||
result |= SAL_MEDIA_DESCRIPTION_CRYPTO_CHANGED;
|
||||
|| (sd1->crypto[i].algo != sd2->crypto[i].algo)){
|
||||
result|=SAL_MEDIA_DESCRIPTION_CRYPTO_POLICY_CHANGED;
|
||||
}
|
||||
if ((strncmp(sd1->crypto[i].master_key, sd2->crypto[i].master_key, sizeof(sd1->crypto[i].master_key) - 1))) {
|
||||
result |= SAL_MEDIA_DESCRIPTION_CRYPTO_KEYS_CHANGED;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -54,6 +54,7 @@ linphone_SOURCES= \
|
|||
conference.c \
|
||||
config-fetching.c \
|
||||
audio_assistant.c \
|
||||
videowindow.c \
|
||||
linphone.h
|
||||
if BUILD_WIZARD
|
||||
linphone_SOURCES+= \
|
||||
|
|
|
|||
|
|
@ -403,7 +403,7 @@ void linphone_gtk_create_in_call_view(LinphoneCall *call){
|
|||
gtk_widget_hide(conf);
|
||||
|
||||
button=linphone_gtk_get_widget(call_view,"terminate_call");
|
||||
image=create_pixmap("stopcall-small.png");
|
||||
image=create_pixmap (linphone_gtk_get_ui_config("stop_call_icon","stopcall-small.png"));
|
||||
gtk_button_set_label(GTK_BUTTON(button),_("Hang up"));
|
||||
gtk_button_set_image(GTK_BUTTON(button),image);
|
||||
gtk_widget_show(image);
|
||||
|
|
@ -687,6 +687,14 @@ void linphone_gtk_in_call_view_show_encryption(LinphoneCall *call){
|
|||
}
|
||||
}
|
||||
|
||||
char *linphone_gtk_address(const LinphoneAddress *addr){
|
||||
const char *displayname=linphone_address_get_display_name(addr);
|
||||
if (!displayname) return linphone_address_as_string_uri_only(addr);
|
||||
return ms_strdup(displayname);
|
||||
}
|
||||
|
||||
|
||||
|
||||
void linphone_gtk_in_call_view_set_in_call(LinphoneCall *call){
|
||||
GtkWidget *callview=(GtkWidget*)linphone_call_get_user_pointer(call);
|
||||
GtkWidget *status=linphone_gtk_get_widget(callview,"in_call_status");
|
||||
|
|
@ -696,6 +704,8 @@ void linphone_gtk_in_call_view_set_in_call(LinphoneCall *call){
|
|||
gboolean in_conf=linphone_call_params_get_local_conference_mode(linphone_call_get_current_params(call));
|
||||
GtkWidget *call_stats=(GtkWidget*)g_object_get_data(G_OBJECT(callview),"call_stats");
|
||||
|
||||
linphone_gtk_in_call_show_video(call);
|
||||
|
||||
display_peer_name_in_label(callee,linphone_call_get_remote_address (call));
|
||||
|
||||
gtk_widget_hide(linphone_gtk_get_widget(callview,"answer_decline_panel"));
|
||||
|
|
@ -736,7 +746,7 @@ void linphone_gtk_in_call_view_set_paused(LinphoneCall *call){
|
|||
GtkWidget *status=linphone_gtk_get_widget(callview,"in_call_status");
|
||||
gtk_widget_hide(linphone_gtk_get_widget(callview,"answer_decline_panel"));
|
||||
gtk_label_set_markup(GTK_LABEL(status),_("<b>Paused call</b>"));
|
||||
|
||||
linphone_gtk_in_call_show_video(call);
|
||||
linphone_gtk_in_call_set_animation_image(callview,GTK_STOCK_MEDIA_PAUSE,TRUE);
|
||||
}
|
||||
|
||||
|
|
@ -760,13 +770,15 @@ static gboolean in_call_view_terminated(LinphoneCall *call){
|
|||
void linphone_gtk_in_call_view_terminate(LinphoneCall *call, const char *error_msg){
|
||||
GtkWidget *callview=(GtkWidget*)linphone_call_get_user_pointer(call);
|
||||
GtkWidget *status;
|
||||
GtkWidget *video_window;
|
||||
gboolean in_conf;
|
||||
guint taskid;
|
||||
if(callview==NULL) return;
|
||||
video_window=(GtkWidget*)g_object_get_data(G_OBJECT(callview),"video_window");
|
||||
status=linphone_gtk_get_widget(callview,"in_call_status");
|
||||
taskid=GPOINTER_TO_INT(g_object_get_data(G_OBJECT(callview),"taskid"));
|
||||
in_conf=linphone_call_params_get_local_conference_mode(linphone_call_get_current_params(call));
|
||||
|
||||
if (video_window) gtk_widget_destroy(video_window);
|
||||
if (status==NULL) return;
|
||||
if (error_msg==NULL)
|
||||
gtk_label_set_markup(GTK_LABEL(status),_("<b>Call ended.</b>"));
|
||||
|
|
|
|||
|
|
@ -48,6 +48,8 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|||
#define LINPHONE_VERSION LINPHONE_VERSION_DATE
|
||||
#endif
|
||||
|
||||
#define LINPHONE_ICON "linphone.png"
|
||||
|
||||
enum {
|
||||
COMPLETION_HISTORY,
|
||||
COMPLETION_LDAP
|
||||
|
|
@ -195,4 +197,6 @@ void linphone_gtk_set_configuration_uri(void);
|
|||
GtkWidget * linphone_gtk_show_config_fetching(void);
|
||||
void linphone_gtk_close_config_fetching(GtkWidget *w, LinphoneConfiguringState state);
|
||||
const char *linphone_gtk_get_sound_path(const char *file);
|
||||
void linphone_gtk_in_call_show_video(LinphoneCall *call);
|
||||
char *linphone_gtk_address(const LinphoneAddress *addr);/*return human readable identifier for a LinphoneAddress */
|
||||
|
||||
|
|
|
|||
102
gtk/main.c
102
gtk/main.c
|
|
@ -48,7 +48,7 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|||
#ifdef ENABLE_NLS
|
||||
#include <locale.h>
|
||||
#endif
|
||||
#define LINPHONE_ICON "linphone.png"
|
||||
|
||||
|
||||
const char *this_program_ident_string="linphone_ident_string=" LINPHONE_VERSION;
|
||||
|
||||
|
|
@ -318,6 +318,7 @@ static void linphone_gtk_init_liblinphone(const char *config_file,
|
|||
g_free(secrets_file);
|
||||
linphone_core_enable_video_capture(the_core, TRUE);
|
||||
linphone_core_enable_video_display(the_core, TRUE);
|
||||
linphone_core_set_native_video_window_id(the_core,-1);/*don't create the window*/
|
||||
if (no_video) {
|
||||
_linphone_gtk_enable_video(FALSE);
|
||||
linphone_gtk_set_ui_config_int("videoselfview",0);
|
||||
|
|
@ -566,102 +567,6 @@ void linphone_gtk_show_about(){
|
|||
gtk_widget_show(about);
|
||||
}
|
||||
|
||||
static void set_video_window_decorations(GdkWindow *w){
|
||||
const char *title=linphone_gtk_get_ui_config("title","Linphone");
|
||||
const char *icon_path=linphone_gtk_get_ui_config("icon",LINPHONE_ICON);
|
||||
char video_title[256];
|
||||
GdkPixbuf *pbuf=create_pixbuf(icon_path);
|
||||
|
||||
if (!linphone_core_in_call(linphone_gtk_get_core())){
|
||||
snprintf(video_title,sizeof(video_title),"%s video",title);
|
||||
/* When not in call, treat the video as a normal window */
|
||||
gdk_window_set_keep_above(w, FALSE);
|
||||
}else{
|
||||
LinphoneAddress *uri =
|
||||
linphone_address_clone(linphone_core_get_current_call_remote_address(linphone_gtk_get_core()));
|
||||
char *display_name;
|
||||
|
||||
linphone_address_clean(uri);
|
||||
if (linphone_address_get_display_name(uri)!=NULL){
|
||||
display_name=ms_strdup(linphone_address_get_display_name(uri));
|
||||
}else{
|
||||
display_name=linphone_address_as_string(uri);
|
||||
}
|
||||
snprintf(video_title,sizeof(video_title),_("Call with %s"),display_name);
|
||||
linphone_address_destroy(uri);
|
||||
ms_free(display_name);
|
||||
|
||||
/* During calls, bring up the video window, arrange so that
|
||||
it is above all the other windows */
|
||||
gdk_window_deiconify(w);
|
||||
gdk_window_set_keep_above(w,TRUE);
|
||||
/* Maybe we should have the following, but then we want to
|
||||
have a timer that turns it off after a little while. */
|
||||
/* gdk_window_set_urgency_hint(w,TRUE); */
|
||||
}
|
||||
gdk_window_set_title(w,video_title);
|
||||
/* Refrain the video window to be closed at all times. */
|
||||
gdk_window_set_functions(w,
|
||||
GDK_FUNC_RESIZE|GDK_FUNC_MOVE|
|
||||
GDK_FUNC_MINIMIZE|GDK_FUNC_MAXIMIZE);
|
||||
if (pbuf){
|
||||
GList *l=NULL;
|
||||
l=g_list_append(l,pbuf);
|
||||
gdk_window_set_icon_list(w,l);
|
||||
g_list_free(l);
|
||||
g_object_unref(G_OBJECT(pbuf));
|
||||
}
|
||||
}
|
||||
|
||||
static gboolean video_needs_update=FALSE;
|
||||
|
||||
static void update_video_title(){
|
||||
video_needs_update=TRUE;
|
||||
}
|
||||
|
||||
static void update_video_titles(LinphoneCore *lc){
|
||||
unsigned long id;
|
||||
static unsigned long previd=0;
|
||||
static unsigned long preview_previd=0;
|
||||
id=linphone_core_get_native_video_window_id(lc);
|
||||
if (id!=previd || video_needs_update){
|
||||
GdkWindow *w;
|
||||
previd=id;
|
||||
if (id!=0){
|
||||
ms_message("Updating window decorations");
|
||||
#ifndef WIN32
|
||||
w=gdk_window_foreign_new((GdkNativeWindow)id);
|
||||
#else
|
||||
w=gdk_window_foreign_new((HANDLE)id);
|
||||
#endif
|
||||
if (w) {
|
||||
set_video_window_decorations(w);
|
||||
g_object_unref(G_OBJECT(w));
|
||||
}
|
||||
else ms_error("gdk_window_foreign_new() failed");
|
||||
if (video_needs_update) video_needs_update=FALSE;
|
||||
}
|
||||
}
|
||||
id=linphone_core_get_native_preview_window_id (lc);
|
||||
if (id!=preview_previd ){
|
||||
GdkWindow *w;
|
||||
preview_previd=id;
|
||||
if (id!=0){
|
||||
ms_message("Updating window decorations for preview");
|
||||
#ifndef WIN32
|
||||
w=gdk_window_foreign_new((GdkNativeWindow)id);
|
||||
#else
|
||||
w=gdk_window_foreign_new((HANDLE)id);
|
||||
#endif
|
||||
if (w) {
|
||||
set_video_window_decorations(w);
|
||||
g_object_unref(G_OBJECT(w));
|
||||
}
|
||||
else ms_error("gdk_window_foreign_new() failed");
|
||||
if (video_needs_update) video_needs_update=FALSE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static gboolean linphone_gtk_iterate(LinphoneCore *lc){
|
||||
static gboolean first_time=TRUE;
|
||||
|
|
@ -677,7 +582,6 @@ static gboolean linphone_gtk_iterate(LinphoneCore *lc){
|
|||
first_time=FALSE;
|
||||
}
|
||||
|
||||
update_video_titles(lc);
|
||||
if (addr_to_call!=NULL){
|
||||
/*make sure we are not showing the login screen*/
|
||||
GtkWidget *mw=linphone_gtk_get_main_window();
|
||||
|
|
@ -928,7 +832,6 @@ void linphone_gtk_call_terminated(LinphoneCall *call, const char *error){
|
|||
}
|
||||
if (linphone_gtk_use_in_call_view() && call)
|
||||
linphone_gtk_in_call_view_terminate(call,error);
|
||||
update_video_title();
|
||||
}
|
||||
|
||||
static void linphone_gtk_update_call_buttons(LinphoneCall *call){
|
||||
|
|
@ -971,7 +874,6 @@ static void linphone_gtk_update_call_buttons(LinphoneCall *call){
|
|||
linphone_gtk_enable_transfer_button(lc,FALSE);
|
||||
linphone_gtk_enable_conference_button(lc,FALSE);
|
||||
}
|
||||
update_video_title();
|
||||
if (call) {
|
||||
linphone_gtk_update_video_button(call);
|
||||
}
|
||||
|
|
|
|||
310
gtk/videowindow.c
Normal file
310
gtk/videowindow.c
Normal file
|
|
@ -0,0 +1,310 @@
|
|||
/*
|
||||
linphone, gtk interface.
|
||||
Copyright (C) 2014 Belledonne Communications SARL
|
||||
|
||||
This program 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 2
|
||||
of the License, or (at your option) any later version.
|
||||
|
||||
This program 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 this program; if not, write to the Free Software
|
||||
Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
||||
*/
|
||||
|
||||
#include "linphone.h"
|
||||
|
||||
#ifdef __linux
|
||||
#include <gdk/gdkx.h>
|
||||
#elif defined(WIN32)
|
||||
#include <gdk/gdkwin32.h>
|
||||
#elif defined(__APPLE__)
|
||||
extern void *gdk_quartz_window_get_nswindow(GdkWindow *window);
|
||||
extern void *gdk_quartz_window_get_nsview(GdkWindow *window);
|
||||
#endif
|
||||
|
||||
#include <gdk/gdkkeysyms.h>
|
||||
|
||||
enum {
|
||||
TARGET_STRING,
|
||||
TARGET_TEXT,
|
||||
TARGET_URILIST
|
||||
};
|
||||
|
||||
static GtkTargetEntry targets[] = {
|
||||
{ "text/uri-list", GTK_TARGET_OTHER_APP, TARGET_URILIST },
|
||||
};
|
||||
|
||||
static void set_video_controls_position(GtkWidget *video_window);
|
||||
|
||||
static void on_end_of_play(LinphonePlayer *player, void *user_data){
|
||||
linphone_player_close(player);
|
||||
}
|
||||
|
||||
static void drag_data_received(GtkWidget *widget, GdkDragContext *context, gint x, gint y,
|
||||
GtkSelectionData *selection_data, guint target_type, guint time, gpointer user_data){
|
||||
int datalen=gtk_selection_data_get_length(selection_data) >= 0;
|
||||
const void *data=gtk_selection_data_get_data(selection_data);
|
||||
LinphoneCall *call=g_object_get_data(G_OBJECT(widget),"call");
|
||||
|
||||
ms_message("target_type=%i, datalen=%i, data=%p",target_type,datalen,data);
|
||||
if (target_type==TARGET_URILIST && data){
|
||||
LinphonePlayer *player=linphone_call_get_player(call);
|
||||
const char *path=(const char*)data;
|
||||
if (player){
|
||||
if (strstr(path,"file://")==path) path+=strlen("file://");
|
||||
if (linphone_player_open(player,path,on_end_of_play,NULL)==0){
|
||||
linphone_player_start(player);
|
||||
}else{
|
||||
GtkWidget *warn=gtk_message_dialog_new(GTK_WINDOW(widget),GTK_DIALOG_MODAL|GTK_DIALOG_DESTROY_WITH_PARENT,
|
||||
GTK_MESSAGE_ERROR,GTK_BUTTONS_CLOSE,
|
||||
_("Cannot play %s."),path);
|
||||
g_signal_connect(warn,"response",(GCallback)gtk_widget_destroy,NULL);
|
||||
gtk_widget_show(warn);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
gtk_drag_finish (context, TRUE, FALSE, time);
|
||||
}
|
||||
|
||||
static gboolean drag_drop(GtkWidget *widget, GdkDragContext *drag_context, gint x, gint y, guint time, gpointer user_data){
|
||||
#if GTK_CHECK_VERSION(2,20,0)
|
||||
GList *l=gdk_drag_context_list_targets(drag_context);
|
||||
GList *elem;
|
||||
|
||||
if (l){
|
||||
ms_message("drag_drop");
|
||||
/* Choose the best target type */
|
||||
for(elem=l;elem!=NULL;elem=g_list_next(elem)){
|
||||
char *name=gdk_atom_name(GDK_POINTER_TO_ATOM(elem->data));
|
||||
ms_message("target: %s",name);
|
||||
g_free(name);
|
||||
}
|
||||
}else{
|
||||
ms_warning("drag_drop no targets");
|
||||
return FALSE;
|
||||
}
|
||||
#endif
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
unsigned long get_native_handle(GdkWindow *gdkw){
|
||||
#ifdef __linux
|
||||
return (unsigned long)GDK_WINDOW_XID(gdkw);
|
||||
#elif defined(WIN32)
|
||||
return (unsigned long)GDK_WINDOW_HWND(gdkw);
|
||||
#elif defined(__APPLE__)
|
||||
return (unsigned long)gdk_quartz_window_get_nsview(gdkw);
|
||||
#endif
|
||||
g_warning("No way to get the native handle from gdk window");
|
||||
return 0;
|
||||
}
|
||||
|
||||
static gint resize_video_window(LinphoneCall *call){
|
||||
const LinphoneCallParams *params=linphone_call_get_current_params(call);
|
||||
if (params){
|
||||
MSVideoSize vsize=linphone_call_params_get_received_video_size(params);
|
||||
if (vsize.width>0 && vsize.height>0){
|
||||
GtkWidget *callview=(GtkWidget*)linphone_call_get_user_pointer(call);
|
||||
GtkWidget *video_window=(GtkWidget*)g_object_get_data(G_OBJECT(callview),"video_window");
|
||||
if (video_window){
|
||||
MSVideoSize cur;
|
||||
gtk_window_get_size(GTK_WINDOW(video_window),&cur.width,&cur.height);
|
||||
if (vsize.width*vsize.height > cur.width*cur.height ||
|
||||
ms_video_size_get_orientation(vsize)!=ms_video_size_get_orientation(cur) ){
|
||||
g_message("Resized to %ix%i",vsize.width,vsize.height);
|
||||
gtk_window_resize(GTK_WINDOW(video_window),vsize.width,vsize.height);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static void on_video_window_destroy(GtkWidget *w, guint timeout){
|
||||
g_source_remove(timeout);
|
||||
linphone_core_set_native_video_window_id(linphone_gtk_get_core(),(unsigned long)-1);
|
||||
}
|
||||
|
||||
static void video_window_set_fullscreen(GtkWidget *w, gboolean val){
|
||||
if (val){
|
||||
g_object_set_data(G_OBJECT(w),"fullscreen",GINT_TO_POINTER(1));
|
||||
gtk_window_fullscreen(GTK_WINDOW(w));
|
||||
}else{
|
||||
g_object_set_data(G_OBJECT(w),"fullscreen",GINT_TO_POINTER(0));
|
||||
gtk_window_unfullscreen(GTK_WINDOW(w));
|
||||
}
|
||||
}
|
||||
/*old names in old version of gdk*/
|
||||
#ifndef GDK_KEY_Escape
|
||||
#define GDK_KEY_Escape GDK_Escape
|
||||
#define GDK_KEY_F GDK_F
|
||||
#define GDK_KEY_f GDK_f
|
||||
#endif
|
||||
|
||||
static void on_video_window_key_press(GtkWidget *w, GdkEvent *ev, gpointer up){
|
||||
g_message("Key press event");
|
||||
switch(ev->key.keyval){
|
||||
case GDK_KEY_f:
|
||||
case GDK_KEY_F:
|
||||
video_window_set_fullscreen(w,TRUE);
|
||||
break;
|
||||
case GDK_KEY_Escape:
|
||||
video_window_set_fullscreen(w,FALSE);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
static void on_controls_response(GtkWidget *dialog, int response_id, GtkWidget *video_window){
|
||||
|
||||
gtk_widget_destroy(dialog);
|
||||
switch(response_id){
|
||||
case GTK_RESPONSE_YES:
|
||||
video_window_set_fullscreen(video_window,TRUE);
|
||||
break;
|
||||
case GTK_RESPONSE_NO:
|
||||
video_window_set_fullscreen(video_window,FALSE);
|
||||
break;
|
||||
case GTK_RESPONSE_REJECT:
|
||||
{
|
||||
LinphoneCall *call=(LinphoneCall*)g_object_get_data(G_OBJECT(video_window),"call");
|
||||
linphone_core_terminate_call(linphone_gtk_get_core(),call);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static void on_controls_destroy(GtkWidget *w){
|
||||
GtkWidget *video_window=(GtkWidget*)g_object_get_data(G_OBJECT(w),"video_window");
|
||||
gint timeout=GPOINTER_TO_INT(g_object_get_data(G_OBJECT(w),"timeout"));
|
||||
if (timeout!=0){
|
||||
g_source_remove(timeout);
|
||||
g_object_set_data(G_OBJECT(w),"timeout",GINT_TO_POINTER(0));
|
||||
}
|
||||
g_object_set_data(G_OBJECT(video_window),"controls",NULL);
|
||||
}
|
||||
|
||||
static gboolean _set_video_controls_position(GtkWidget *video_window){
|
||||
GtkWidget *w=(GtkWidget*)g_object_get_data(G_OBJECT(video_window),"controls");
|
||||
if (w){
|
||||
gint vw,vh;
|
||||
gint cw,ch;
|
||||
gint x,y;
|
||||
gtk_window_get_size(GTK_WINDOW(video_window),&vw,&vh);
|
||||
gtk_window_get_position(GTK_WINDOW(video_window),&x,&y);
|
||||
gtk_window_get_size(GTK_WINDOW(w),&cw,&ch);
|
||||
gtk_window_move(GTK_WINDOW(w),x+vw/2 - cw/2, y + vh - ch);
|
||||
}
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
static void set_video_controls_position(GtkWidget *video_window){
|
||||
/*do it a first time*/
|
||||
_set_video_controls_position(video_window);
|
||||
/*and schedule to do it a second time in order to workaround a bug in fullscreen mode, where poistion is not taken into account the first time*/
|
||||
g_timeout_add(0,(GSourceFunc)_set_video_controls_position,video_window);
|
||||
}
|
||||
|
||||
static gboolean video_window_moved(GtkWidget *widget, GdkEvent *event, gpointer user_data){
|
||||
set_video_controls_position(widget);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
static GtkWidget *show_video_controls(GtkWidget *video_window){
|
||||
GtkWidget *w;
|
||||
w=(GtkWidget*)g_object_get_data(G_OBJECT(video_window),"controls");
|
||||
if (!w){
|
||||
gboolean isfullscreen=GPOINTER_TO_INT(g_object_get_data(G_OBJECT(video_window),"fullscreen"));
|
||||
const char *stock_button=isfullscreen ? GTK_STOCK_LEAVE_FULLSCREEN : GTK_STOCK_FULLSCREEN;
|
||||
gint response_id=isfullscreen ? GTK_RESPONSE_NO : GTK_RESPONSE_YES ;
|
||||
gint timeout;
|
||||
GtkWidget *button;
|
||||
w=gtk_dialog_new_with_buttons("",GTK_WINDOW(video_window),GTK_DIALOG_DESTROY_WITH_PARENT,stock_button,response_id,NULL);
|
||||
gtk_window_set_opacity(GTK_WINDOW(w),0.5);
|
||||
gtk_window_set_decorated(GTK_WINDOW(w),FALSE);
|
||||
button=gtk_button_new_with_label(_("Hang up"));
|
||||
gtk_button_set_image(GTK_BUTTON(button),create_pixmap (linphone_gtk_get_ui_config("stop_call_icon","stopcall-small.png")));
|
||||
gtk_widget_show(button);
|
||||
gtk_dialog_add_action_widget(GTK_DIALOG(w),button,GTK_RESPONSE_REJECT);
|
||||
g_signal_connect(w,"response",(GCallback)on_controls_response,video_window);
|
||||
timeout=g_timeout_add(3000,(GSourceFunc)gtk_widget_destroy,w);
|
||||
g_object_set_data(G_OBJECT(w),"timeout",GINT_TO_POINTER(timeout));
|
||||
g_signal_connect(w,"destroy",(GCallback)on_controls_destroy,NULL);
|
||||
g_object_set_data(G_OBJECT(w),"video_window",video_window);
|
||||
g_object_set_data(G_OBJECT(video_window),"controls",w);
|
||||
set_video_controls_position(video_window);
|
||||
gtk_widget_show(w);
|
||||
}else{
|
||||
gint timeout=GPOINTER_TO_INT(g_object_get_data(G_OBJECT(w),"timeout"));
|
||||
g_source_remove(timeout);
|
||||
timeout=g_timeout_add(3000,(GSourceFunc)gtk_widget_destroy,w);
|
||||
g_object_set_data(G_OBJECT(w),"timeout",GINT_TO_POINTER(timeout));
|
||||
}
|
||||
return w;
|
||||
}
|
||||
|
||||
static GtkWidget *create_video_window(LinphoneCall *call){
|
||||
char *remote,*title;
|
||||
GtkWidget *video_window;
|
||||
const LinphoneAddress *addr;
|
||||
const char *icon_path=linphone_gtk_get_ui_config("icon",LINPHONE_ICON);
|
||||
GdkPixbuf *pbuf=create_pixbuf(icon_path);
|
||||
guint timeout;
|
||||
MSVideoSize vsize=MS_VIDEO_SIZE_CIF;
|
||||
GdkColor color;
|
||||
|
||||
addr=linphone_call_get_remote_address(call);
|
||||
remote=linphone_gtk_address(addr);
|
||||
video_window=gtk_window_new(GTK_WINDOW_TOPLEVEL);
|
||||
title=g_strdup_printf("%s - Video call with %s",linphone_gtk_get_ui_config("title","Linphone"),remote);
|
||||
ms_free(remote);
|
||||
gtk_window_set_title(GTK_WINDOW(video_window),title);
|
||||
g_free(title);
|
||||
if (pbuf){
|
||||
gtk_window_set_icon(GTK_WINDOW(video_window),pbuf);
|
||||
}
|
||||
gtk_window_resize(GTK_WINDOW(video_window),vsize.width,vsize.height);
|
||||
gdk_color_parse("black",&color);
|
||||
gtk_widget_modify_bg(video_window,GTK_STATE_NORMAL,&color);
|
||||
|
||||
gtk_drag_dest_set(video_window, GTK_DEST_DEFAULT_ALL, targets, sizeof(targets)/sizeof(GtkTargetEntry), GDK_ACTION_COPY);
|
||||
gtk_widget_show(video_window);
|
||||
gdk_window_set_events(gtk_widget_get_window(video_window),
|
||||
gdk_window_get_events(gtk_widget_get_window(video_window)) | GDK_POINTER_MOTION_MASK);
|
||||
timeout=g_timeout_add(500,(GSourceFunc)resize_video_window,call);
|
||||
g_signal_connect(video_window,"destroy",(GCallback)on_video_window_destroy,GINT_TO_POINTER(timeout));
|
||||
g_signal_connect(video_window,"key-press-event",(GCallback)on_video_window_key_press,NULL);
|
||||
g_signal_connect_swapped(video_window,"motion-notify-event",(GCallback)show_video_controls,video_window);
|
||||
g_signal_connect(video_window,"configure-event",(GCallback)video_window_moved,NULL);
|
||||
g_signal_connect(video_window, "drag-data-received",(GCallback)drag_data_received, NULL);
|
||||
g_signal_connect(video_window, "drag-drop",(GCallback)drag_drop, NULL);
|
||||
g_object_set_data(G_OBJECT(video_window),"call",call);
|
||||
return video_window;
|
||||
}
|
||||
|
||||
void linphone_gtk_in_call_show_video(LinphoneCall *call){
|
||||
GtkWidget *callview=(GtkWidget*)linphone_call_get_user_pointer(call);
|
||||
GtkWidget *video_window=(GtkWidget*)g_object_get_data(G_OBJECT(callview),"video_window");
|
||||
const LinphoneCallParams *params=linphone_call_get_current_params(call);
|
||||
LinphoneCore *lc=linphone_gtk_get_core();
|
||||
|
||||
if (linphone_call_get_state(call)!=LinphoneCallPaused && params && linphone_call_params_video_enabled(params)){
|
||||
if (video_window==NULL){
|
||||
video_window=create_video_window(call);
|
||||
g_object_set_data(G_OBJECT(callview),"video_window",video_window);
|
||||
}
|
||||
linphone_core_set_native_video_window_id(lc,get_native_handle(gtk_widget_get_window(video_window)));
|
||||
}else{
|
||||
if (video_window){
|
||||
gtk_widget_destroy(video_window);
|
||||
g_object_set_data(G_OBJECT(callview),"video_window",NULL);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -68,13 +68,15 @@ typedef enum {
|
|||
SalTransportDTLS /*DTLS*/
|
||||
}SalTransport;
|
||||
|
||||
#define SAL_MEDIA_DESCRIPTION_UNCHANGED 0x00
|
||||
#define SAL_MEDIA_DESCRIPTION_NETWORK_CHANGED 0x01
|
||||
#define SAL_MEDIA_DESCRIPTION_CODEC_CHANGED 0x02
|
||||
#define SAL_MEDIA_DESCRIPTION_CRYPTO_CHANGED 0x04
|
||||
#define SAL_MEDIA_DESCRIPTION_STREAMS_CHANGED 0x08
|
||||
#define SAL_MEDIA_DESCRIPTION_UNCHANGED 0x00
|
||||
#define SAL_MEDIA_DESCRIPTION_NETWORK_CHANGED (1)
|
||||
#define SAL_MEDIA_DESCRIPTION_CODEC_CHANGED (1<<1)
|
||||
#define SAL_MEDIA_DESCRIPTION_CRYPTO_KEYS_CHANGED (1<<2)
|
||||
#define SAL_MEDIA_DESCRIPTION_CRYPTO_POLICY_CHANGED (1<<3)
|
||||
#define SAL_MEDIA_DESCRIPTION_STREAMS_CHANGED (1<<4)
|
||||
|
||||
#define SAL_MEDIA_DESCRIPTION_CHANGED (SAL_MEDIA_DESCRIPTION_NETWORK_CHANGED | SAL_MEDIA_DESCRIPTION_CODEC_CHANGED |\
|
||||
SAL_MEDIA_DESCRIPTION_CRYPTO_CHANGED |SAL_MEDIA_DESCRIPTION_STREAMS_CHANGED)
|
||||
SAL_MEDIA_DESCRIPTION_CRYPTO_KEYS_CHANGED |SAL_MEDIA_DESCRIPTION_CRYPTO_POLICY_CHANGED | SAL_MEDIA_DESCRIPTION_STREAMS_CHANGED)
|
||||
|
||||
const char* sal_transport_to_string(SalTransport transport);
|
||||
SalTransport sal_transport_parse(const char*);
|
||||
|
|
|
|||
|
|
@ -1 +1 @@
|
|||
Subproject commit 21e35e89ffa8920bb0b5865d365b84471ecfa321
|
||||
Subproject commit 91f2782073c776b2d5ce3ab0a12561aea7610068
|
||||
2
oRTP
2
oRTP
|
|
@ -1 +1 @@
|
|||
Subproject commit 45da3ab75d39587189ea95829ee1cb92d61827be
|
||||
Subproject commit 540ee49bd3f65139f7e5938cc6bc1f8a4353c3f7
|
||||
|
|
@ -22,7 +22,8 @@ liblinphonetester_la_SOURCES = tester.c \
|
|||
stun_tester.c \
|
||||
remote_provisioning_tester.c \
|
||||
quality_reporting_tester.c \
|
||||
transport_tester.c
|
||||
transport_tester.c \
|
||||
player_tester.c
|
||||
|
||||
liblinphonetester_la_LDFLAGS= -no-undefined
|
||||
liblinphonetester_la_LIBADD= ../coreapi/liblinphone.la $(CUNIT_LIBS)
|
||||
|
|
|
|||
|
|
@ -25,10 +25,16 @@
|
|||
#include "lpconfig.h"
|
||||
#include "private.h"
|
||||
#include "liblinphone_tester.h"
|
||||
#include "mediastreamer2/dsptools.h"
|
||||
|
||||
#ifdef WIN32
|
||||
#define unlink _unlink
|
||||
#endif
|
||||
|
||||
static void srtp_call(void);
|
||||
static void call_base(LinphoneMediaEncryption mode, bool_t enable_video,bool_t enable_relay,LinphoneFirewallPolicy policy);
|
||||
static void disable_all_audio_codecs_except_one(LinphoneCore *lc, const char *mime, int rate);
|
||||
static char *create_filepath(const char *dir, const char *filename, const char *ext);
|
||||
|
||||
// prototype definition for call_recording()
|
||||
#ifdef ANDROID
|
||||
|
|
@ -775,6 +781,7 @@ static void call_with_no_sdp(void) {
|
|||
linphone_core_manager_destroy(pauline);
|
||||
}
|
||||
|
||||
|
||||
static bool_t check_ice(LinphoneCoreManager* caller, LinphoneCoreManager* callee, LinphoneIceState state) {
|
||||
LinphoneCall *c1,*c2;
|
||||
bool_t audio_success=FALSE;
|
||||
|
|
@ -1878,6 +1885,114 @@ static void call_with_declined_srtp(void) {
|
|||
linphone_core_manager_destroy(pauline);
|
||||
}
|
||||
|
||||
static void on_eof(LinphonePlayer *player, void *user_data){
|
||||
LinphoneCoreManager *marie=(LinphoneCoreManager*)user_data;
|
||||
marie->stat.number_of_player_eof++;
|
||||
}
|
||||
|
||||
static void call_with_file_player(void) {
|
||||
LinphoneCoreManager* marie = linphone_core_manager_new( "marie_rc");
|
||||
LinphoneCoreManager* pauline = linphone_core_manager_new( "pauline_rc");
|
||||
LinphonePlayer *player;
|
||||
char hellopath[256];
|
||||
char *recordpath = create_filepath(liblinphone_tester_writable_dir_prefix, "record", "wav");
|
||||
double similar;
|
||||
|
||||
/*make sure the record file doesn't already exists, otherwise this test will append new samples to it*/
|
||||
unlink(recordpath);
|
||||
|
||||
snprintf(hellopath,sizeof(hellopath), "%s/sounds/hello8000.wav", liblinphone_tester_file_prefix);
|
||||
|
||||
/*caller uses soundcard*/
|
||||
|
||||
/*callee is recording and plays file*/
|
||||
linphone_core_use_files(pauline->lc,TRUE);
|
||||
linphone_core_set_play_file(pauline->lc,hellopath);
|
||||
linphone_core_set_record_file(pauline->lc,recordpath);
|
||||
|
||||
CU_ASSERT_TRUE(call(marie,pauline));
|
||||
|
||||
player=linphone_call_get_player(linphone_core_get_current_call(marie->lc));
|
||||
CU_ASSERT_PTR_NOT_NULL(player);
|
||||
if (player){
|
||||
CU_ASSERT_TRUE(linphone_player_open(player,hellopath,on_eof,marie)==0);
|
||||
CU_ASSERT_TRUE(linphone_player_start(player)==0);
|
||||
}
|
||||
CU_ASSERT_TRUE(wait_for_until(pauline->lc,marie->lc,&marie->stat.number_of_player_eof,1,12000));
|
||||
|
||||
/*just to sleep*/
|
||||
linphone_core_terminate_all_calls(marie->lc);
|
||||
CU_ASSERT_TRUE(wait_for(pauline->lc,marie->lc,&pauline->stat.number_of_LinphoneCallEnd,1));
|
||||
CU_ASSERT_TRUE(wait_for(pauline->lc,marie->lc,&marie->stat.number_of_LinphoneCallEnd,1));
|
||||
CU_ASSERT_TRUE(ms_audio_diff(hellopath,recordpath,&similar,NULL,NULL)==0);
|
||||
CU_ASSERT_TRUE(similar>0.9);
|
||||
CU_ASSERT_TRUE(similar<=1.0);
|
||||
linphone_core_manager_destroy(marie);
|
||||
linphone_core_manager_destroy(pauline);
|
||||
ms_free(recordpath);
|
||||
}
|
||||
|
||||
static bool_t is_format_supported(LinphoneCore *lc, const char *fmt){
|
||||
const char **formats=linphone_core_get_supported_file_formats(lc);
|
||||
for(;*formats!=NULL;++formats){
|
||||
if (strcasecmp(*formats,fmt)==0) return TRUE;
|
||||
}
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
static void call_with_mkv_file_player(void) {
|
||||
LinphoneCoreManager* marie = linphone_core_manager_new( "marie_rc");
|
||||
LinphoneCoreManager* pauline = linphone_core_manager_new( "pauline_rc");
|
||||
LinphonePlayer *player;
|
||||
char hellomkv[256];
|
||||
char hellowav[256];
|
||||
char *recordpath;
|
||||
double similar;
|
||||
|
||||
if (!is_format_supported(marie->lc,"mkv")){
|
||||
ms_warning("Test skipped, no mkv support.");
|
||||
goto end;
|
||||
}
|
||||
recordpath = create_filepath(liblinphone_tester_writable_dir_prefix, "record", "wav");
|
||||
/*make sure the record file doesn't already exists, otherwise this test will append new samples to it*/
|
||||
unlink(recordpath);
|
||||
|
||||
snprintf(hellowav,sizeof(hellowav), "%s/sounds/hello8000.wav", liblinphone_tester_file_prefix);
|
||||
snprintf(hellomkv,sizeof(hellomkv), "%s/sounds/hello8000.mkv", liblinphone_tester_file_prefix);
|
||||
|
||||
/*caller uses soundcard*/
|
||||
|
||||
/*callee is recording and plays file*/
|
||||
linphone_core_use_files(pauline->lc,TRUE);
|
||||
linphone_core_set_play_file(pauline->lc,hellowav); /*just to send something but we are not testing what is sent by pauline*/
|
||||
linphone_core_set_record_file(pauline->lc,recordpath);
|
||||
|
||||
CU_ASSERT_TRUE(call(marie,pauline));
|
||||
|
||||
player=linphone_call_get_player(linphone_core_get_current_call(marie->lc));
|
||||
CU_ASSERT_PTR_NOT_NULL(player);
|
||||
if (player){
|
||||
CU_ASSERT_TRUE(linphone_player_open(player,hellomkv,on_eof,marie)==0);
|
||||
CU_ASSERT_TRUE(linphone_player_start(player)==0);
|
||||
}
|
||||
CU_ASSERT_TRUE(wait_for_until(pauline->lc,marie->lc,&marie->stat.number_of_player_eof,1,12000));
|
||||
|
||||
/*just to sleep*/
|
||||
linphone_core_terminate_all_calls(marie->lc);
|
||||
CU_ASSERT_TRUE(wait_for(pauline->lc,marie->lc,&pauline->stat.number_of_LinphoneCallEnd,1));
|
||||
CU_ASSERT_TRUE(wait_for(pauline->lc,marie->lc,&marie->stat.number_of_LinphoneCallEnd,1));
|
||||
CU_ASSERT_TRUE(ms_audio_diff(hellowav,recordpath,&similar,NULL,NULL)==0);
|
||||
CU_ASSERT_TRUE(similar>0.9);
|
||||
CU_ASSERT_TRUE(similar<=1.0);
|
||||
ms_free(recordpath);
|
||||
|
||||
end:
|
||||
linphone_core_manager_destroy(marie);
|
||||
linphone_core_manager_destroy(pauline);
|
||||
|
||||
}
|
||||
|
||||
|
||||
static void call_base(LinphoneMediaEncryption mode, bool_t enable_video,bool_t enable_relay,LinphoneFirewallPolicy policy) {
|
||||
LinphoneCoreManager* marie = linphone_core_manager_new( "marie_rc");
|
||||
LinphoneCoreManager* pauline = linphone_core_manager_new( "pauline_rc");
|
||||
|
|
@ -2808,13 +2923,7 @@ static void savpf_to_savpf_call(void) {
|
|||
}
|
||||
|
||||
static char *create_filepath(const char *dir, const char *filename, const char *ext) {
|
||||
char *filepath = ms_new0(char, strlen(dir) + strlen(filename) + strlen(ext) + 3);
|
||||
strcpy(filepath, dir);
|
||||
strcat(filepath, "/");
|
||||
strcat(filepath, filename);
|
||||
strcat(filepath, ".");
|
||||
strcat(filepath, ext);
|
||||
return filepath;
|
||||
return ms_strdup_printf("%s/%s.%s",dir,filename,ext);
|
||||
}
|
||||
|
||||
static void record_call(const char *filename, bool_t enableVideo) {
|
||||
|
|
@ -2867,7 +2976,6 @@ static void record_call(const char *filename, bool_t enableVideo) {
|
|||
linphone_call_stop_recording(callInst);
|
||||
end_call(marie, pauline);
|
||||
CU_ASSERT_EQUAL(access(filepath, F_OK), 0);
|
||||
remove(filepath);
|
||||
}
|
||||
ms_free(filepath);
|
||||
}
|
||||
|
|
@ -2949,7 +3057,57 @@ static void call_with_in_dialog_update(void) {
|
|||
belle_sip_object_dump_active_objects();
|
||||
}
|
||||
}
|
||||
static void call_with_in_dialog_codec_change_base(bool_t no_sdp) {
|
||||
int begin;
|
||||
int leaked_objects;
|
||||
int dummy=0;
|
||||
LinphoneCoreManager* marie;
|
||||
LinphoneCoreManager* pauline;
|
||||
LinphoneCallParams *params;
|
||||
|
||||
belle_sip_object_enable_leak_detector(TRUE);
|
||||
begin=belle_sip_object_get_object_count();
|
||||
|
||||
marie = linphone_core_manager_new( "marie_rc");
|
||||
pauline = linphone_core_manager_new( "pauline_rc");
|
||||
CU_ASSERT_TRUE(call(pauline,marie));
|
||||
liblinphone_tester_check_rtcp(marie,pauline);
|
||||
params=linphone_core_create_call_params(marie->lc,linphone_core_get_current_call(marie->lc));
|
||||
|
||||
linphone_core_enable_payload_type(pauline->lc,linphone_core_find_payload_type(pauline->lc,"PCMU",8000,1),FALSE); /*disable PCMU*/
|
||||
linphone_core_enable_payload_type(marie->lc,linphone_core_find_payload_type(marie->lc,"PCMU",8000,1),FALSE); /*disable PCMU*/
|
||||
linphone_core_enable_payload_type(pauline->lc,linphone_core_find_payload_type(pauline->lc,"PCMA",8000,1),TRUE); /*enable PCMA*/
|
||||
linphone_core_enable_payload_type(marie->lc,linphone_core_find_payload_type(marie->lc,"PCMA",8000,1),TRUE); /*enable PCMA*/
|
||||
if (no_sdp) {
|
||||
linphone_core_enable_sdp_200_ack(marie->lc,TRUE);
|
||||
}
|
||||
linphone_core_update_call(marie->lc,linphone_core_get_current_call(marie->lc),params);
|
||||
linphone_call_params_destroy(params);
|
||||
CU_ASSERT_TRUE(wait_for(marie->lc,pauline->lc,&marie->stat.number_of_LinphoneCallUpdating,1));
|
||||
CU_ASSERT_TRUE(wait_for(marie->lc,pauline->lc,&marie->stat.number_of_LinphoneCallStreamsRunning,2));
|
||||
CU_ASSERT_TRUE(wait_for(marie->lc,pauline->lc,&pauline->stat.number_of_LinphoneCallUpdatedByRemote,1));
|
||||
CU_ASSERT_TRUE(wait_for(marie->lc,pauline->lc,&pauline->stat.number_of_LinphoneCallStreamsRunning,2));
|
||||
CU_ASSERT_STRING_EQUAL("PCMA",linphone_payload_type_get_mime_type(linphone_call_params_get_used_audio_codec(linphone_call_get_current_params(linphone_core_get_current_call(marie->lc)))));
|
||||
wait_for_until(marie->lc, pauline->lc, &dummy, 1, 3000);
|
||||
CU_ASSERT_TRUE(linphone_call_get_audio_stats(linphone_core_get_current_call(marie->lc))->download_bandwidth>70);
|
||||
CU_ASSERT_TRUE(linphone_call_get_audio_stats(linphone_core_get_current_call(pauline->lc))->download_bandwidth>70);
|
||||
|
||||
end_call(marie,pauline);
|
||||
linphone_core_manager_destroy(marie);
|
||||
linphone_core_manager_destroy(pauline);
|
||||
|
||||
leaked_objects=belle_sip_object_get_object_count()-begin;
|
||||
CU_ASSERT_TRUE(leaked_objects==0);
|
||||
if (leaked_objects>0){
|
||||
belle_sip_object_dump_active_objects();
|
||||
}
|
||||
}
|
||||
static void call_with_in_dialog_codec_change(void) {
|
||||
call_with_in_dialog_codec_change_base(FALSE);
|
||||
}
|
||||
static void call_with_in_dialog_codec_change_no_sdp(void) {
|
||||
call_with_in_dialog_codec_change_base(TRUE);
|
||||
}
|
||||
static void call_with_custom_supported_tags(void) {
|
||||
int begin;
|
||||
int leaked_objects;
|
||||
|
|
@ -3015,6 +3173,8 @@ test_t call_tests[] = {
|
|||
{ "ZRTP call",zrtp_call},
|
||||
{ "ZRTP video call",zrtp_video_call},
|
||||
{ "SRTP call with declined srtp", call_with_declined_srtp },
|
||||
{ "Call with file player", call_with_file_player},
|
||||
{ "Call with mkv file player", call_with_mkv_file_player},
|
||||
#ifdef VIDEO_ENABLED
|
||||
{ "Simple video call",video_call},
|
||||
{ "Simple video call using policy",video_call_using_policy},
|
||||
|
|
@ -3079,6 +3239,8 @@ test_t call_tests[] = {
|
|||
{ "SAVPF to SAVP call", savpf_to_savp_call },
|
||||
{ "SAVPF to SAVPF call", savpf_to_savpf_call },
|
||||
{ "Call with in-dialog UPDATE request", call_with_in_dialog_update },
|
||||
{ "Call with in-dialog codec change", call_with_in_dialog_codec_change },
|
||||
{ "Call with in-dialog codec change no sdp", call_with_in_dialog_codec_change_no_sdp },
|
||||
{ "Call with custom supported tags", call_with_custom_supported_tags }
|
||||
};
|
||||
|
||||
|
|
|
|||
|
|
@ -13,17 +13,16 @@ RPIGEkQ2wzG9AJq7iJ2Yy8+2kTvULajvhI0JrSqVbgS9Z9fUKgCN6oIZfvQsrxus
|
|||
UcIc3KjqaP1mLw7aIpUCQH5S0B+GOwKa8+RbuRcgBvksqkRwRZn6jawoNJJSBCDn
|
||||
gQJ5B9PvJXppTsbnulSD2srhUqCR1pzGfnl8bYV8b8Q=
|
||||
-----END RSA PRIVATE KEY-----
|
||||
|
||||
Certificate:
|
||||
Data:
|
||||
Version: 3 (0x2)
|
||||
Serial Number: 5 (0x5)
|
||||
Serial Number: 9 (0x9)
|
||||
Signature Algorithm: sha1WithRSAEncryption
|
||||
Issuer: C=FR, ST=Some-State, L=Grenoble, O=Belledonne Communications, OU=LAB, CN=Jehan Monnier/emailAddress=jehan.monnier@belledonne-communications.com
|
||||
Validity
|
||||
Not Before: Sep 23 15:58:58 2013 GMT
|
||||
Not After : Sep 23 15:58:58 2014 GMT
|
||||
Subject: C=FR, ST=France, L=Grenoble, O=Belledonne Communications, OU=LAB, CN=See altname for DNS name/emailAddress=jehan.monnier@belledonne-communications.com
|
||||
Not Before: Sep 25 16:12:35 2014 GMT
|
||||
Not After : Sep 22 16:12:35 2024 GMT
|
||||
Subject: C=FR, ST=France, L=Grenoble, O=Belledonne Communications, OU=LAB, CN=Jehan Monnier/emailAddress=jehan.monnier@belledonne-communications.com
|
||||
Subject Public Key Info:
|
||||
Public Key Algorithm: rsaEncryption
|
||||
Public-Key: (1024 bit)
|
||||
|
|
@ -46,31 +45,31 @@ Certificate:
|
|||
X509v3 Subject Alternative Name:
|
||||
DNS:altname.linphone.org, DNS:*.wildcard2.linphone.org
|
||||
Signature Algorithm: sha1WithRSAEncryption
|
||||
21:05:d3:36:82:5d:f4:f4:70:71:17:ac:06:12:49:0c:d6:c3:
|
||||
21:07:9c:2f:79:c8:14:da:e5:3a:92:04:22:5b:74:cf:53:3c:
|
||||
95:33:51:93:66:04:59:c6:3d:dd:22:cf:3f:f8:0e:24:93:6b:
|
||||
2a:02:f7:bf:ba:89:1b:72:9a:d4:1b:bf:22:3d:08:51:13:a4:
|
||||
bf:43:d2:89:a1:c5:f2:e3:04:24:1e:d4:33:64:06:83:2d:b6:
|
||||
66:34:16:a9:f4:8d:6f:3f:71:86:ab:73:19:36:ae:43:29:7e:
|
||||
9d:6c:35:3a:75:f4:22:8b:c5:e3:1e:ee:c1:0d:d7:63:cc:95:
|
||||
4a:6a
|
||||
56:f5:23:64:4c:8d:85:6e:05:d6:42:a3:41:b2:6a:ab:a1:cd:
|
||||
be:ae:4a:38:c5:23:4c:62:2c:06:4d:49:b7:fc:ad:86:1d:9b:
|
||||
c0:7e:33:80:fa:7d:31:8b:ca:9c:28:44:b2:1c:f1:ed:73:5b:
|
||||
d3:80:72:b0:6c:0b:20:2b:e5:2b:02:c6:be:14:ad:55:34:2f:
|
||||
6f:8e:bb:7b:61:ce:9c:af:85:a7:b0:cd:d1:4e:1e:17:e9:7e:
|
||||
61:ed:50:60:9a:de:d0:7a:6d:a5:ee:04:9a:5c:41:94:21:e5:
|
||||
05:61:a8:17:ab:eb:b4:cc:7f:90:9b:3a:0e:ca:31:fb:65:40:
|
||||
11:2d
|
||||
-----BEGIN CERTIFICATE-----
|
||||
MIIDSjCCArOgAwIBAgIBBTANBgkqhkiG9w0BAQUFADCBuzELMAkGA1UEBhMCRlIx
|
||||
MIIDPzCCAqigAwIBAgIBCTANBgkqhkiG9w0BAQUFADCBuzELMAkGA1UEBhMCRlIx
|
||||
EzARBgNVBAgMClNvbWUtU3RhdGUxETAPBgNVBAcMCEdyZW5vYmxlMSIwIAYDVQQK
|
||||
DBlCZWxsZWRvbm5lIENvbW11bmljYXRpb25zMQwwCgYDVQQLDANMQUIxFjAUBgNV
|
||||
BAMMDUplaGFuIE1vbm5pZXIxOjA4BgkqhkiG9w0BCQEWK2plaGFuLm1vbm5pZXJA
|
||||
YmVsbGVkb25uZS1jb21tdW5pY2F0aW9ucy5jb20wHhcNMTMwOTIzMTU1ODU4WhcN
|
||||
MTQwOTIzMTU1ODU4WjCBwjELMAkGA1UEBhMCRlIxDzANBgNVBAgMBkZyYW5jZTER
|
||||
YmVsbGVkb25uZS1jb21tdW5pY2F0aW9ucy5jb20wHhcNMTQwOTI1MTYxMjM1WhcN
|
||||
MjQwOTIyMTYxMjM1WjCBtzELMAkGA1UEBhMCRlIxDzANBgNVBAgMBkZyYW5jZTER
|
||||
MA8GA1UEBwwIR3Jlbm9ibGUxIjAgBgNVBAoMGUJlbGxlZG9ubmUgQ29tbXVuaWNh
|
||||
dGlvbnMxDDAKBgNVBAsMA0xBQjEhMB8GA1UEAwwYU2VlIGFsdG5hbWUgZm9yIERO
|
||||
UyBuYW1lMTowOAYJKoZIhvcNAQkBFitqZWhhbi5tb25uaWVyQGJlbGxlZG9ubmUt
|
||||
Y29tbXVuaWNhdGlvbnMuY29tMIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDH
|
||||
ZG78iwkkxJeq3ZPuQwY9DfdcNCvHXayW+5p5VUULV50ohJKtJJzhp5ysq4VH7q/d
|
||||
mOnMnbYTACnqVSlph88zRdQJd/g0h6T4DyWa5Jxe+R1hwLWVfgeSXstCK8m9SwxK
|
||||
qnqA5mPZxfARXg3r4XWkUK2A1lWIXCkZU3MMD4JJ4QIDAQABo1UwUzAJBgNVHRME
|
||||
AjAAMAsGA1UdDwQEAwIF4DA5BgNVHREEMjAwghRhbHRuYW1lLmxpbnBob25lLm9y
|
||||
Z4IYKi53aWxkY2FyZDIubGlucGhvbmUub3JnMA0GCSqGSIb3DQEBBQUAA4GBACEF
|
||||
0zaCXfT0cHEXrAYSSQzWwyEHnC95yBTa5TqSBCJbdM9TPJUzUZNmBFnGPd0izz/4
|
||||
DiSTayoC97+6iRtymtQbvyI9CFETpL9D0omhxfLjBCQe1DNkBoMttmY0Fqn0jW8/
|
||||
cYarcxk2rkMpfp1sNTp19CKLxeMe7sEN12PMlUpq
|
||||
dGlvbnMxDDAKBgNVBAsMA0xBQjEWMBQGA1UEAwwNSmVoYW4gTW9ubmllcjE6MDgG
|
||||
CSqGSIb3DQEJARYramVoYW4ubW9ubmllckBiZWxsZWRvbm5lLWNvbW11bmljYXRp
|
||||
b25zLmNvbTCBnzANBgkqhkiG9w0BAQEFAAOBjQAwgYkCgYEAx2Ru/IsJJMSXqt2T
|
||||
7kMGPQ33XDQrx12slvuaeVVFC1edKISSrSSc4aecrKuFR+6v3ZjpzJ22EwAp6lUp
|
||||
aYfPM0XUCXf4NIek+A8lmuScXvkdYcC1lX4Hkl7LQivJvUsMSqp6gOZj2cXwEV4N
|
||||
6+F1pFCtgNZViFwpGVNzDA+CSeECAwEAAaNVMFMwCQYDVR0TBAIwADALBgNVHQ8E
|
||||
BAMCBeAwOQYDVR0RBDIwMIIUYWx0bmFtZS5saW5waG9uZS5vcmeCGCoud2lsZGNh
|
||||
cmQyLmxpbnBob25lLm9yZzANBgkqhkiG9w0BAQUFAAOBgQBW9SNkTI2FbgXWQqNB
|
||||
smqroc2+rko4xSNMYiwGTUm3/K2GHZvAfjOA+n0xi8qcKESyHPHtc1vTgHKwbAsg
|
||||
K+UrAsa+FK1VNC9vjrt7Yc6cr4WnsM3RTh4X6X5h7VBgmt7Qem2l7gSaXEGUIeUF
|
||||
YagXq+u0zH+QmzoOyjH7ZUARLQ==
|
||||
-----END CERTIFICATE-----
|
||||
|
|
|
|||
|
|
@ -39,7 +39,7 @@ default_ca = CA_default # The default ca section
|
|||
####################################################################
|
||||
[ CA_default ]
|
||||
|
||||
dir = ./demoCA # Where everything is kept
|
||||
dir = . # Where everything is kept
|
||||
certs = $dir/certs # Where the issued certs are kept
|
||||
crl_dir = $dir/crl # Where the issued crl are kept
|
||||
database = $dir/index.txt # database index file.
|
||||
|
|
|
|||
|
|
@ -39,7 +39,7 @@ default_ca = CA_default # The default ca section
|
|||
####################################################################
|
||||
[ CA_default ]
|
||||
|
||||
dir = ./demoCA # Where everything is kept
|
||||
dir = . # Where everything is kept
|
||||
certs = $dir/certs # Where the issued certs are kept
|
||||
crl_dir = $dir/crl # Where the issued crl are kept
|
||||
database = $dir/index.txt # database index file.
|
||||
|
|
|
|||
|
|
@ -59,6 +59,7 @@ extern test_suite_t stun_test_suite;
|
|||
extern test_suite_t remote_provisioning_test_suite;
|
||||
extern test_suite_t quality_reporting_test_suite;
|
||||
extern test_suite_t transport_test_suite;
|
||||
extern test_suite_t player_test_suite;
|
||||
|
||||
|
||||
extern int liblinphone_tester_nb_test_suites(void);
|
||||
|
|
@ -195,6 +196,7 @@ typedef struct _stats {
|
|||
int number_of_LinphoneCallEncryptedOff;
|
||||
int number_of_NetworkReachableTrue;
|
||||
int number_of_NetworkReachableFalse;
|
||||
int number_of_player_eof;
|
||||
LinphoneChatMessage* last_received_chat_message;
|
||||
}stats;
|
||||
|
||||
|
|
|
|||
|
|
@ -281,7 +281,7 @@ static void text_message_with_privacy(void) {
|
|||
/* make sure lime is not enabled */
|
||||
linphone_core_set_lime(marie->lc, 0);
|
||||
linphone_core_set_lime(pauline->lc, 0);
|
||||
|
||||
|
||||
to = linphone_address_as_string(marie->identity);
|
||||
chat_room = linphone_core_create_chat_room(pauline->lc,to);
|
||||
ms_free(to);
|
||||
|
|
|
|||
64
tester/player_tester.c
Normal file
64
tester/player_tester.c
Normal file
|
|
@ -0,0 +1,64 @@
|
|||
#include "liblinphone_tester.h"
|
||||
|
||||
static bool_t wait_for_eof(bool_t *eof, int *time,int time_refresh, int timeout) {
|
||||
while(*time < timeout && !*eof) {
|
||||
usleep(time_refresh * 1000U);
|
||||
*time += time_refresh;
|
||||
}
|
||||
return *time < timeout;
|
||||
}
|
||||
|
||||
static void eof_callback(LinphonePlayer *player, void *user_data) {
|
||||
bool_t *eof = (bool_t *)user_data;
|
||||
*eof = TRUE;
|
||||
}
|
||||
|
||||
static void play_file(const char *filename, bool_t unsupported_format) {
|
||||
LinphoneCoreManager *lc_manager;
|
||||
LinphonePlayer *player;
|
||||
int res, time = 0;
|
||||
bool_t eof = FALSE;
|
||||
|
||||
lc_manager = linphone_core_manager_new("marie_rc");
|
||||
CU_ASSERT_PTR_NOT_NULL(lc_manager);
|
||||
if(lc_manager == NULL) return;
|
||||
|
||||
player = linphone_core_create_file_player(lc_manager->lc, ms_snd_card_manager_get_default_card(ms_snd_card_manager_get()), video_stream_get_default_video_renderer());
|
||||
CU_ASSERT_PTR_NOT_NULL(player);
|
||||
if(player == NULL) goto fail;
|
||||
|
||||
res = linphone_player_open(player, filename, eof_callback, &eof);
|
||||
if(unsupported_format) {
|
||||
CU_ASSERT_EQUAL(res, -1);
|
||||
} else {
|
||||
CU_ASSERT_EQUAL(res, 0);
|
||||
}
|
||||
if(res == -1) goto fail;
|
||||
|
||||
CU_ASSERT_EQUAL((res = linphone_player_start(player)), 0);
|
||||
if(res == -1) goto fail;
|
||||
|
||||
CU_ASSERT_TRUE(wait_for_eof(&eof, &time, 100, 13000));
|
||||
|
||||
linphone_player_close(player);
|
||||
|
||||
fail:
|
||||
if(player) linphone_file_player_destroy(player);
|
||||
if(lc_manager) linphone_core_manager_destroy(lc_manager);
|
||||
}
|
||||
|
||||
static void playing_test(void) {
|
||||
play_file("sounds/hello_opus_h264.mkv", !linphone_file_player_matroska_supported());
|
||||
}
|
||||
|
||||
test_t player_tests[] = {
|
||||
{ "Playing" , playing_test }
|
||||
};
|
||||
|
||||
test_suite_t player_test_suite = {
|
||||
"Player",
|
||||
NULL,
|
||||
NULL,
|
||||
sizeof(player_tests) / sizeof(test_t),
|
||||
player_tests
|
||||
};
|
||||
BIN
tester/sounds/hello8000.mkv
Normal file
BIN
tester/sounds/hello8000.mkv
Normal file
Binary file not shown.
BIN
tester/sounds/hello_opus_h264.mkv
Normal file
BIN
tester/sounds/hello_opus_h264.mkv
Normal file
Binary file not shown.
|
|
@ -388,6 +388,7 @@ void liblinphone_tester_init(void) {
|
|||
add_test_suite(&remote_provisioning_test_suite);
|
||||
add_test_suite(&quality_reporting_test_suite);
|
||||
add_test_suite(&transport_test_suite);
|
||||
add_test_suite(&player_test_suite);
|
||||
}
|
||||
|
||||
void liblinphone_tester_uninit(void) {
|
||||
|
|
|
|||
|
|
@ -59,7 +59,7 @@ static char* get_public_contact_ip(LinphoneCore* lc) {
|
|||
ms_free(contact);
|
||||
return ms_strdup(contact_host_ip);
|
||||
}
|
||||
static void call_with_transport_base(bool_t use_tunnel, bool_t with_sip, LinphoneMediaEncryption encryption) {
|
||||
static void call_with_transport_base(LinphoneTunnelMode tunnel_mode, bool_t with_sip, LinphoneMediaEncryption encryption) {
|
||||
if (linphone_core_tunnel_available()){
|
||||
char *tmp_char;
|
||||
LinphoneCoreManager *pauline = linphone_core_manager_new( "pauline_rc");
|
||||
|
|
@ -69,7 +69,7 @@ static void call_with_transport_base(bool_t use_tunnel, bool_t with_sip, Linphon
|
|||
LinphoneAddress *server_addr = linphone_address_new(linphone_proxy_config_get_server_addr(proxy));
|
||||
LinphoneAddress *route = linphone_address_new(linphone_proxy_config_get_route(proxy));
|
||||
const char * tunnel_ip = get_ip_from_hostname("tunnel.linphone.org");
|
||||
char *public_ip;
|
||||
char *public_ip, *public_ip2=NULL;
|
||||
|
||||
CU_ASSERT_TRUE(wait_for(pauline->lc,NULL,&pauline->stat.number_of_LinphoneRegistrationOk,1));
|
||||
public_ip = get_public_contact_ip(pauline->lc);
|
||||
|
|
@ -77,7 +77,7 @@ static void call_with_transport_base(bool_t use_tunnel, bool_t with_sip, Linphon
|
|||
|
||||
linphone_core_set_media_encryption(pauline->lc, encryption);
|
||||
|
||||
if (use_tunnel){
|
||||
if (tunnel_mode != LinphoneTunnelModeDisable){
|
||||
LinphoneTunnel *tunnel = linphone_core_get_tunnel(pauline->lc);
|
||||
LinphoneTunnelConfig *config = linphone_tunnel_config_new();
|
||||
|
||||
|
|
@ -91,24 +91,30 @@ static void call_with_transport_base(bool_t use_tunnel, bool_t with_sip, Linphon
|
|||
tmp_char = linphone_address_as_string(route);
|
||||
linphone_proxy_config_set_route(proxy, tmp_char);
|
||||
ms_free(tmp_char);
|
||||
linphone_tunnel_set_mode(tunnel, LinphoneTunnelModeEnable);
|
||||
if(with_sip) linphone_tunnel_enable_sip(tunnel, with_sip);
|
||||
linphone_tunnel_config_set_host(config, "tunnel.linphone.org");
|
||||
linphone_tunnel_config_set_port(config, 443);
|
||||
linphone_tunnel_config_set_remote_udp_mirror_port(config, 12345);
|
||||
linphone_tunnel_add_server(tunnel, config);
|
||||
linphone_tunnel_set_mode(tunnel, tunnel_mode);
|
||||
linphone_tunnel_enable_sip(tunnel, with_sip);
|
||||
linphone_proxy_config_done(proxy);
|
||||
|
||||
/*enabling the tunnel cause another REGISTER to be made*/
|
||||
CU_ASSERT_TRUE(wait_for(pauline->lc,NULL,&pauline->stat.number_of_LinphoneRegistrationOk,2));
|
||||
|
||||
/* Ensure that we did use the tunnel. If so, we should see contact changed from:
|
||||
Contact: <sip:pauline@192.168.0.201>;.[...]
|
||||
To:
|
||||
Contact: <sip:pauline@91.121.209.194:43867>;[....] (91.121.209.194 must be tunnel.liphone.org)
|
||||
*/
|
||||
ms_free(public_ip);
|
||||
public_ip = get_public_contact_ip(pauline->lc);
|
||||
CU_ASSERT_STRING_EQUAL(public_ip, tunnel_ip);
|
||||
if(tunnel_mode == LinphoneTunnelModeEnable) {
|
||||
/* Ensure that we did use the tunnel. If so, we should see contact changed from:
|
||||
Contact: <sip:pauline@192.168.0.201>;.[...]
|
||||
To:
|
||||
Contact: <sip:pauline@91.121.209.194:43867>;[....] (91.121.209.194 must be tunnel.liphone.org)
|
||||
*/
|
||||
ms_free(public_ip);
|
||||
public_ip = get_public_contact_ip(pauline->lc);
|
||||
CU_ASSERT_STRING_EQUAL(public_ip, tunnel_ip);
|
||||
} else {
|
||||
public_ip2 = get_public_contact_ip(pauline->lc);
|
||||
CU_ASSERT_STRING_EQUAL(public_ip, public_ip2);
|
||||
}
|
||||
}
|
||||
|
||||
CU_ASSERT_TRUE(call(pauline,marie));
|
||||
|
|
@ -121,6 +127,7 @@ static void call_with_transport_base(bool_t use_tunnel, bool_t with_sip, Linphon
|
|||
end_call(pauline,marie);
|
||||
|
||||
ms_free(public_ip);
|
||||
if(public_ip2 != NULL) ms_free(public_ip2);
|
||||
linphone_address_destroy(server_addr);
|
||||
linphone_address_destroy(route);
|
||||
linphone_core_manager_destroy(pauline);
|
||||
|
|
@ -131,21 +138,31 @@ static void call_with_transport_base(bool_t use_tunnel, bool_t with_sip, Linphon
|
|||
}
|
||||
|
||||
static void call_with_tunnel(void) {
|
||||
call_with_transport_base(TRUE, TRUE, LinphoneMediaEncryptionNone);
|
||||
call_with_transport_base(LinphoneTunnelModeEnable, TRUE, LinphoneMediaEncryptionNone);
|
||||
}
|
||||
|
||||
static void call_with_tunnel_srtp(void) {
|
||||
call_with_transport_base(TRUE, TRUE, LinphoneMediaEncryptionSRTP);
|
||||
call_with_transport_base(LinphoneTunnelModeEnable, TRUE, LinphoneMediaEncryptionSRTP);
|
||||
}
|
||||
|
||||
static void call_with_tunnel_without_sip(void) {
|
||||
call_with_transport_base(TRUE, FALSE, LinphoneMediaEncryptionNone);
|
||||
call_with_transport_base(LinphoneTunnelModeEnable, FALSE, LinphoneMediaEncryptionNone);
|
||||
}
|
||||
|
||||
static void call_with_tunnel_auto(void) {
|
||||
call_with_transport_base(LinphoneTunnelModeAuto, TRUE, LinphoneMediaEncryptionNone);
|
||||
}
|
||||
|
||||
static void call_with_tunnel_auto_without_sip_with_srtp(void) {
|
||||
call_with_transport_base(LinphoneTunnelModeAuto, FALSE, LinphoneMediaEncryptionSRTP);
|
||||
}
|
||||
|
||||
test_t transport_tests[] = {
|
||||
{ "Tunnel only", call_with_tunnel },
|
||||
{ "Tunnel with SRTP", call_with_tunnel_srtp },
|
||||
{ "Tunnel without SIP", call_with_tunnel_without_sip }
|
||||
{ "Tunnel without SIP", call_with_tunnel_without_sip },
|
||||
{ "Tunnel in automatic mode", call_with_tunnel_auto },
|
||||
{ "Tunnel in automatic mode with SRTP without SIP", call_with_tunnel_auto_without_sip_with_srtp },
|
||||
};
|
||||
|
||||
test_suite_t transport_test_suite = {
|
||||
|
|
|
|||
55
tools/CMakeLists.txt
Normal file
55
tools/CMakeLists.txt
Normal file
|
|
@ -0,0 +1,55 @@
|
|||
############################################################################
|
||||
# CMakeLists.txt
|
||||
# Copyright (C) 2014 Belledonne Communications, Grenoble France
|
||||
#
|
||||
############################################################################
|
||||
#
|
||||
# This program 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 2
|
||||
# of the License, or (at your option) any later version.
|
||||
#
|
||||
# This program 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 this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
||||
#
|
||||
############################################################################
|
||||
|
||||
if(MSVC)
|
||||
find_library(LIBGCC NAMES gcc)
|
||||
find_library(LIBMINGWEX NAMES mingwex)
|
||||
endif()
|
||||
|
||||
set(LP_GEN_WRAPPERS_SOURCE_FILES
|
||||
generator.cc
|
||||
generator.hh
|
||||
genwrappers.cc
|
||||
software-desc.cc
|
||||
software-desc.hh
|
||||
)
|
||||
|
||||
add_definitions(
|
||||
-DIN_LINPHONE
|
||||
)
|
||||
|
||||
set(LP_GEN_WRAPPERS_LIBS
|
||||
${LIBGCC}
|
||||
${LIBMINGWEX}
|
||||
${XML2_LIBRARIES}
|
||||
)
|
||||
|
||||
add_executable(lp-gen-wrappers ${LP_GEN_WRAPPERS_SOURCE_FILES})
|
||||
target_link_libraries(lp-gen-wrappers ${LP_GEN_WRAPPERS_LIBS})
|
||||
|
||||
|
||||
install(TARGETS lp-gen-wrappers
|
||||
RUNTIME DESTINATION bin
|
||||
LIBRARY DESTINATION lib
|
||||
ARCHIVE DESTINATION lib
|
||||
PERMISSIONS OWNER_READ OWNER_WRITE OWNER_EXECUTE GROUP_READ GROUP_EXECUTE WORLD_READ WORLD_EXECUTE
|
||||
)
|
||||
|
|
@ -46,6 +46,7 @@ blacklisted_functions = [
|
|||
'linphone_chat_message_start_file_download', # to be handwritten because of callback
|
||||
'linphone_chat_message_state_to_string', # There is no use to wrap this function
|
||||
'linphone_chat_room_create_file_transfer_message', # missing LinphoneContent
|
||||
'linphone_core_add_listener',
|
||||
'linphone_core_can_we_add_call', # private function
|
||||
'linphone_core_get_audio_port_range', # to be handwritten because of result via arguments
|
||||
'linphone_core_get_sip_transports', # missing LCSipTransports
|
||||
|
|
@ -54,6 +55,7 @@ blacklisted_functions = [
|
|||
'linphone_core_get_video_policy', # missing LinphoneVideoPolicy
|
||||
'linphone_core_get_video_port_range', # to be handwritten because of result via arguments
|
||||
'linphone_core_publish', # missing LinphoneContent
|
||||
'linphone_core_remove_listener',
|
||||
'linphone_core_serialize_logs', # There is no use to wrap this function
|
||||
'linphone_core_set_log_file', # There is no use to wrap this function
|
||||
'linphone_core_set_log_handler', # Hand-written but put directly in the linphone module
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue