Commit 2ee8dbb5 authored by alexandresavard's avatar alexandresavard
Browse files

Merge branch 'master' into recording

Conflicts:

	src/audio/audiortp.cpp
	src/sipvoiplink.cpp
parents 007abd23 9c27daf4
/*
* Copyright (C) 2009 Savoir-Faire Linux inc.
* Author: Emmanuel Milou <emmanuel.milou@savoirfairelinux.com>
*
* 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 3 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., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef PLUGIN_H
#define PLUGIN_H
#include <string>
#include "global.h"
#include "pluginmanager.h"
/*
* @file plugin.h
* @brief Define a plugin object
*/
namespace sflphone {
class PluginManager;
class Plugin {
public:
Plugin( const std::string &name );
//Plugin( const Plugin &plugin );
virtual ~Plugin() {}
public:
/**
* Return the minimal core version required so that the plugin could work
* @return int The version required
*/
virtual int getCoreVersion() const = 0;
/**
* Register the plugin to the plugin manager
*/
virtual void registerPlugin( PluginManager & ) = 0;
private:
Plugin &operator =(const Plugin &plugin);
};
}
class Plugin {
public:
Plugin( const std::string &name ){
_name = name;
}
virtual ~Plugin() {}
inline std::string getPluginName (void) { return _name; }
/**
* Return the minimal core version required so that the plugin could work
* @return int The version required
*/
virtual int initFunc (PluginInfo **info) = 0;
private:
Plugin &operator =(const Plugin &plugin);
std::string _name;
};
typedef Plugin* createFunc (void);
typedef void destroyFunc (Plugin*);
#endif //PLUGIN_H
/*
* Copyright (C) 2009 Savoir-Faire Linux inc.
* Author: Emmanuel Milou <emmanuel.milou@savoirfairelinux.com>
*
* 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 3 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., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <dirent.h>
#include <dlfcn.h>
#include "pluginmanager.h"
::sflphone::PluginManager::PluginManager():_loadedPlugins()
PluginManager* PluginManager::_instance = 0;
PluginManager*
PluginManager::instance()
{
if(!_instance){
return new PluginManager();
}
return _instance;
}
PluginManager::PluginManager()
:_loadedPlugins()
{
_instance = this;
}
::sflphone::PluginManager::~PluginManager()
PluginManager::~PluginManager()
{
_instance = 0;
}
int ::sflphone::PluginManager::loadPlugins( const std::string &path )
int
PluginManager::loadPlugins (const std::string &path)
{
std::string pluginDir, current;
::sflphone::Plugin *plugin;
DIR *dir;
dirent *dirStruct;
int result=0;
LibraryManager *library;
Plugin *plugin;
const std::string pDir = "..";
const std::string cDir = ".";
......@@ -37,62 +69,163 @@ int ::sflphone::PluginManager::loadPlugins( const std::string &path )
current = dirStruct->d_name;
/* Test if the current item is not the parent or the current directory */
if( current != pDir && current != cDir ){
loadDynamicLibrary( current );
result++;
}
}
/* Load the dynamic library */
library = loadDynamicLibrary( pluginDir + current );
/* Instanciate the plugin object */
if(instanciatePlugin (library, &plugin) != 0)
{
_debug("Error instanciating the plugin ...\n");
return 1;
}
/* Regitering the current plugin */
if(registerPlugin (plugin, library) != 0)
{
_debug("Error registering the plugin ...\n");
return 1;
}
}
}
}
else
return 1;
/* Close the directory */
closedir( dir );
return result;
return 0;
}
::sflphone::Plugin* ::sflphone::PluginManager::isPluginLoaded( const std::string &name )
int
PluginManager::unloadPlugins (void)
{
if(_loadedPlugins.empty()) return NULL;
PluginInfo *info;
if(_loadedPlugins.empty()) return 0;
/* Use an iterator on the loaded plugins map */
pluginMap::iterator iter;
iter = _loadedPlugins.begin();
while( iter != _loadedPlugins.end() ) {
if ( iter->first == name ) {
/* Return the associated plugin */
return iter->second;
info = iter->second;
if (deletePlugin (info) != 0)
{
_debug("Error deleting the plugin ... \n");
return 1;
}
unloadDynamicLibrary (info->_libraryPtr);
if (unregisterPlugin (info) != 0)
{
_debug("Error unregistering the plugin ... \n");
return 1;
}
iter++;
}
return 0;
}
bool
PluginManager::isPluginLoaded (const std::string &name)
{
if(_loadedPlugins.empty()) return false;
/* Use an iterator on the loaded plugins map */
pluginMap::iterator iter;
iter = _loadedPlugins.find (name);
/* If we are here, it means that the plugin we were looking for has not been loaded */
return NULL;
/* Returns map::end if the specified key has not been found */
if(iter==_loadedPlugins.end())
return false;
/* Returns the plugin pointer */
return true;
}
void* ::sflphone::PluginManager::loadDynamicLibrary( const std::string& filename ) {
void *pluginHandlePtr = NULL;
const char *error;
LibraryManager*
PluginManager::loadDynamicLibrary (const std::string& filename)
{
/* Load the library through the library manager */
return new LibraryManager (filename);
}
_debug("Loading dynamic library %s\n", filename.c_str());
int
PluginManager::unloadDynamicLibrary (LibraryManager *libraryPtr)
{
_debug("Unloading dynamic library ...\n");
/* Close it */
return libraryPtr->unloadLibrary ();
}
#if defined(Q_OS_UNIX)
/* Load the library */
pluginHandlePtr = dlopen( filename.c_str(), RTLD_LAZY );
if( !pluginHandlePtr ) {
error = dlerror();
_debug("Error while opening plug-in: %s\n", error);
}
dlerror();
#endif
int
PluginManager::instanciatePlugin (LibraryManager *libraryPtr, Plugin **plugin)
{
createFunc *createPlugin;
LibraryManager::SymbolHandle symbol;
if (libraryPtr->resolveSymbol ("createPlugin", &symbol) != 0)
return 1;
createPlugin = (createFunc*)symbol;
*plugin = createPlugin();
return 0;
}
return pluginHandlePtr;
int
PluginManager::deletePlugin (PluginInfo *plugin)
{
destroyFunc *destroyPlugin;
LibraryManager::SymbolHandle symbol;
if (plugin->_libraryPtr->resolveSymbol ("destroyPlugin", &symbol) != 0)
return 1;
destroyPlugin = (destroyFunc*)symbol;
/* Call it */
destroyPlugin (plugin->_plugin);
return 0;
}
void ::sflphone::PluginManager::unloadDynamicLibrary( void * pluginHandlePtr ) {
int
PluginManager::registerPlugin (Plugin *plugin, LibraryManager *library)
{
std::string key;
PluginInfo *p_info;
if( plugin==0 )
return 1;
dlclose( pluginHandlePtr );
dlerror();
p_info = new PluginInfo();
/* Retrieve information from the plugin */
plugin->initFunc (&p_info);
key = p_info->_name;
//p_info->_plugin = plugin;
p_info->_libraryPtr = library;
/* Add the data in the loaded plugin map */
_loadedPlugins[ key ] = p_info;
return 0;
}
::sflphone::PluginManager* ::sflphone::PluginManager::_instance = 0;
int
PluginManager::unregisterPlugin (PluginInfo *plugin)
{
pluginMap::iterator iter;
std::string key;
key = plugin->_name;
if (!isPluginLoaded(key))
return 1;
iter = _loadedPlugins.find (key);
_loadedPlugins.erase (iter);
return 0;
}
/*
* Copyright (C) 2009 Savoir-Faire Linux inc.
* Author: Emmanuel Milou <emmanuel.milou@savoirfairelinux.com>
*
* 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 3 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., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef PLUGIN_MANAGER_H
#define PLUGIN_MANAGER_H
......@@ -6,67 +25,87 @@
* @brief Base class of the plugin manager
*/
#include "plugin.h"
#include "librarymanager.h"
#include "global.h"
#include <map>
#include <string>
#include <vector>
class Plugin;
typedef struct PluginInfo {
std::string _name;
LibraryManager *_libraryPtr;
Plugin *_plugin;
int _major_version;
int _minor_version;
} PluginInfo;
#include "plugin.h"
class PluginManager {
public:
/**
* Destructor
*/
~PluginManager();
/**
* Returns the unique instance of the plugin manager
*/
static PluginManager* instance();
/**
* Load all the plugins found in a specific directory
* @param path The absolute path to the directory
* @return int The number of items loaded
*/
int loadPlugins (const std::string &path = "");
int unloadPlugins (void);
int instanciatePlugin (LibraryManager* libraryPtr, Plugin** plugin);
/**
* Check if a plugin has been already loaded
* @param name The name of the plugin looked for
* @return bool The pointer on the plugin or NULL if not found
*/
bool isPluginLoaded (const std::string &name);
int registerPlugin (Plugin *plugin, LibraryManager *library);
int unregisterPlugin (PluginInfo *plugin);
int deletePlugin (PluginInfo *plugin);
/**
* Load a unix dynamic/shared library
* @param filename The path to the dynamic/shared library
* @return LibraryManager* A pointer on the library
*/
LibraryManager* loadDynamicLibrary (const std::string &filename);
/**
* Unload a unix dynamic/shared library
* @param LibraryManager* The pointer on the loaded library
*/
int unloadDynamicLibrary (LibraryManager* libraryPtr);
private:
/**
* Default constructor
*/
PluginManager();
/* Map of plugins associated by their string name */
typedef std::map<std::string, PluginInfo*> pluginMap;
pluginMap _loadedPlugins;
/* The unique static instance */
static PluginManager* _instance;
namespace sflphone {
class PluginManager {
public:
/**
* Default constructor
*/
PluginManager();
/**
* Destructor
*/
~PluginManager();
/**
* Returns the unique instance of the plugin manager
*/
static PluginManager* instance();
/**
* Load all the plugins found in a specific directory
* @param path The absolute path to the directory
* @return int The number of items loaded
*/
int loadPlugins( const std::string &path = "" );
/**
* Check if a plugin has been already loaded
* @param name The name of the plugin looked for
* @return Plugin* The pointer on the plugin or NULL if not found
*/
Plugin* isPluginLoaded( const std::string &name );
private:
/**
* Load a unix dynamic/shared library
* @param filename The path to the dynamic/shared library
* @return void* A pointer on it
*/
void * loadDynamicLibrary( const std::string &filename );
/**
* Unload a unix dynamic/shared library
* @param pluginHandleptr The pointer on the loaded plugin
*/
void unloadDynamicLibrary( void * pluginHandlePtr );
/* Map of plugins associated by their string name */
typedef std::map<std::string, ::sflphone::Plugin*> pluginMap;
pluginMap _loadedPlugins;
/* The unique static instance */
static PluginManager* _instance;
};
}
};
#endif //PLUGIN_MANAGER_H
include $(top_srcdir)/globals.mak
PLUGIN_LIB = libplugintest.so
libplugintest_so_SOURCES = pluginTest.cpp
libplugintest_so_CXXFLAGS = -fPIC -g -Wall
libplugintest_so_LDFLAGS = --shared -lc
INSTALL_PLUGIN_RULE = install-libplugintest_so
noinst_PROGRAMS = libplugintest.so
install-exec-local: install-libplugintest_so
uninstall-local: uninstall-libplugintest_so
install-libplugintest_so: libplugintest.so
mkdir -p $(sflplugindir)
$(INSTALL_PROGRAM) libplugintest.so $(sflplugindir)
uninstall-libplugintest_so:
rm -f $(sflplugindir)/libplugintest.so
/*
* Copyright (C) 2009 Savoir-Faire Linux inc.
* Author: Emmanuel Milou <emmanuel.milou@savoirfairelinux.com>
*
* 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 3 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., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include "../plugin.h"
#define MAJOR_VERSION 1
#define MINOR_VERSION 0
class PluginTest : public Plugin {
public:
PluginTest( const std::string &name )
:Plugin( name ) {
}
virtual int initFunc (PluginInfo **info) {
(*info)->_plugin = this;
(*info)->_major_version = MAJOR_VERSION;
(*info)->_minor_version = MINOR_VERSION;
(*info)->_name = getPluginName();
return 0;
}
};
extern "C" Plugin* createPlugin (void){
return new PluginTest("mytest");
}
extern "C" void destroyPlugin (Plugin *p){
delete p;
}
......@@ -154,9 +154,6 @@ SIPVoIPLink* SIPVoIPLink::_instance = NULL;
// to get random number for RANDOM_PORT
srand (time(NULL));
/* Instanciate the C++ thread */
_evThread = new EventThread(this);
/* Start pjsip initialization step */
init();
}
......@@ -190,6 +187,10 @@ bool SIPVoIPLink::init()
{
if(initDone())
return false;
/* Instanciate the C++ thread */
_evThread = new EventThread(this);
/* Initialize the pjsip library */
pjsip_init();
initDone(true);
......@@ -200,7 +201,9 @@ bool SIPVoIPLink::init()
void
SIPVoIPLink::terminate()
{
delete _evThread; _evThread = NULL;
if (_evThread){
delete _evThread; _evThread = NULL;
}
/* Clean shutdown of pjsip library */
if( initDone() )
......@@ -213,7 +216,6 @@ SIPVoIPLink::terminate()
void
SIPVoIPLink::terminateSIPCall()
{
_debug("SIPVoIPLink::terminateSIPCall(): function called \n");
ost::MutexLock m(_callMapMutex);
CallMap::iterator iter = _callMap.begin();
SIPCall *call;
......@@ -234,9 +236,7 @@ SIPVoIPLink::terminateOneCall(const CallID& id)
{
_debug("SIPVoIPLink::terminateOneCall(): function called \n");