diff --git a/src/audio/tonegenerator.cpp b/src/audio/tonegenerator.cpp index 9bbc64327b55e6b5b3b0dd07f80786e984a699da..ea21beeecaa999d2ffe0c2e1fb890107d1026251 100644 --- a/src/audio/tonegenerator.cpp +++ b/src/audio/tonegenerator.cpp @@ -364,6 +364,7 @@ ToneGenerator::playRingtone (const char *fileName) { // read data as a block: file.read (_src,length); + file.close(); // Decode file.ul expandedsize = _ulaw->codecDecode (_dst, (unsigned char *)_src, length); @@ -373,7 +374,6 @@ ToneGenerator::playRingtone (const char *fileName) { tonethread->start(); } - file.close(); return 1; } diff --git a/src/gui/guiframework.cpp b/src/gui/guiframework.cpp index e2f11ed328a9ceec46238a5d3b338e79d0ac83b7..06baf09a9608340adbd8cb2899cfa53a9c5f48bd 100644 --- a/src/gui/guiframework.cpp +++ b/src/gui/guiframework.cpp @@ -24,7 +24,6 @@ using namespace std; #include "guiframework.h" #include "../manager.h" - GuiFramework::GuiFramework () {} @@ -217,9 +216,9 @@ GuiFramework::getZeroconf(const std::string& sequenceId) } bool -GuiFramework::attachZeroconfEvents(const std::string& sequenceId) +GuiFramework::attachZeroconfEvents(const std::string& sequenceId, Observer& observer) { - return Manager::instance().attachZeroconfEvents(sequenceId, *this); + return Manager::instance().attachZeroconfEvents(sequenceId, observer); } bool diff --git a/src/gui/guiframework.h b/src/gui/guiframework.h index 7690eb071e613874fa16890d72b0a34e8b2fa344..725b40c7cc741c701197602702752f2e3cad1698 100644 --- a/src/gui/guiframework.h +++ b/src/gui/guiframework.h @@ -25,9 +25,8 @@ #include <string> #include "server/argtokenizer.h" -#include "../observer.h" -class GuiFramework : public Pattern::Observer { +class GuiFramework { public: GuiFramework (); virtual ~GuiFramework (void); @@ -82,7 +81,7 @@ public: // config bool getZeroconf(const std::string& sequenceId); - bool attachZeroconfEvents(const std::string& sequenceId); + bool attachZeroconfEvents(const std::string& sequenceId, Observer& observer); bool getCallStatus(const std::string& sequenceId); bool getConfigAll(const std::string& sequenceId); bool getConfig(const std::string& section, const std::string& name, TokenList& arg); diff --git a/src/gui/server/requestconfig.cpp b/src/gui/server/requestconfig.cpp index 1fde8987e9498298d4d9c4727732b95589114489..358a7e35be8324eb6979b651b28ff87b661593bd 100644 --- a/src/gui/server/requestconfig.cpp +++ b/src/gui/server/requestconfig.cpp @@ -41,13 +41,24 @@ RequestZeroconf::execute() ResponseMessage RequestZeroconfEvent::execute() { - if (GUIServer::instance().attachZeroconfEvents(_sequenceId)) { + if (GUIServer::instance().attachZeroconfEvents(_sequenceId, *this)) { return message("200", "OK"); } else { return message("501","Zeroconf not enabled or activated"); } } +RequestZeroconfEvent::~RequestZeroconfEvent() +{ + GUIServer::instance.removeZeroconfEvents(*this); +} + +ResponseMessage +RequestZeroconfEvent::update() +{ + return message("100", "New Zeroconf events - Not Implemented"); +} + ResponseMessage RequestCallStatus::execute() { diff --git a/src/gui/server/requestconfig.h b/src/gui/server/requestconfig.h index 8566453c2471cb258e5c275aca48d7ba7ad9508d..5a5a577d7f00be167438d007843975079f96d93e 100644 --- a/src/gui/server/requestconfig.h +++ b/src/gui/server/requestconfig.h @@ -21,7 +21,7 @@ #define __REQUESTCONFIG_H__ #include "request.h" - +#include "../../observer.h" class RequestGetEvents : public RequestGlobal { public: @@ -36,9 +36,10 @@ public: }; -class RequestZeroconfEvent : public RequestGlobal { +class RequestZeroconfEvent : public RequestGlobal, public Pattern::Observer { public: RequestZeroconfEvent(const std::string &sequenceId, const TokenList& argList) : RequestGlobal(sequenceId,argList) {} + ~RequestZeroconfEvent(); ResponseMessage execute(); }; diff --git a/src/managerimpl.cpp b/src/managerimpl.cpp index f58af4d59b61686217c3427d0a8132537f9ee541..c8c8424150e81392e53fdfc45d4aa92427ecb7dd 100644 --- a/src/managerimpl.cpp +++ b/src/managerimpl.cpp @@ -1038,7 +1038,7 @@ ManagerImpl::getStunInfo (StunAddress4& stunSvrAddr) { _debug("Opened a stun socket pair FAILED\n"); } } - +/* AudioDevice ManagerImpl::deviceList (int index) { @@ -1073,6 +1073,7 @@ ManagerImpl::defaultDevice (int index) } return defaultDisplayed; } +*/ bool ManagerImpl::useStun (void) { @@ -1252,11 +1253,11 @@ ManagerImpl::selectAudioDriver (void) void ManagerImpl::initZeroconf(void) { - _useZeroconf = getConfigInt(PREFERENCES, CONFIG_ZEROCONF); + int useZeroconf = getConfigInt(PREFERENCES, CONFIG_ZEROCONF); #ifdef USE_ZEROCONF - if (_useZeroconf) { - _DNSService->scanServices(); + if (useZeroconf) { + _DNSService->startScanServices(); } #endif } @@ -1281,28 +1282,30 @@ ManagerImpl::getZeroconf(const std::string& sequenceId) { bool returnValue = false; #ifdef USE_ZEROCONF - if (_useZeroconf && _gui != NULL) { + int useZeroconf = getConfigInt(PREFERENCES, CONFIG_ZEROCONF); + if (useZeroconf && _gui != NULL) { TokenList arg; TokenList argTXT; std::string newService = "new service"; std::string newTXT = "new txt record"; + if (!_DNSService->isStart()) { _DNSService->startScanServices(); } DNSServiceMap services = _DNSService->getServices(); DNSServiceMap::iterator iter = services.begin(); arg.push_back(newService); while(iter!=services.end()) { - arg.push_first(iter->first); - _gui.sendMessage("100",sequenceId,arg); - arg.pop_first(); // remove the first, the name + arg.push_front(iter->first); + _gui->sendMessage("100",sequenceId,arg); + arg.pop_front(); // remove the first, the name TXTRecordMap record = iter->second.getTXTRecords(); TXTRecordMap::iterator iterTXT = record.begin(); while(iterTXT!=record.end()) { - argTXT.flush(); + argTXT.clear(); argTXT.push_back(iter->first); argTXT.push_back(iterTXT->first); argTXT.push_back(iterTXT->second); argTXT.push_back(newTXT); - _gui.sendMessage("101",sequenceId,arg); + _gui->sendMessage("101",sequenceId,argTXT); iterTXT++; } iter++; @@ -1317,20 +1320,31 @@ ManagerImpl::getZeroconf(const std::string& sequenceId) * Main Thread */ bool -ManagerImpl::attachZeroconfEvents(const std::string& sequenceId, const Pattern::Observer &observer) +ManagerImpl::attachZeroconfEvents(const std::string& sequenceId, Pattern::Observer& observer) { bool returnValue = false; // don't need the _gui like getZeroconf function // because Observer is here #ifdef USE_ZEROCONF - if (_useZeroconf) { - _DNSService->attach(sequenceId,observer); + int useZeroconf = getConfigInt(PREFERENCES, CONFIG_ZEROCONF); + if (useZeroconf) { + if (!_DNSService->isStart()) { _DNSService->startScanServices(); } + _DNSService->attach(observer); returnValue = true; } #endif return returnValue; } - +bool +ManagerImpl::detachZeroconfEvents(Pattern::Observer& observer) +{ + bool returnValue = false; +#ifdef USE_ZEROCONF + _DNSService->detach(observer); + returnValue = true; +#endif + return returnValue; +} /** * Main Thread */ @@ -1476,10 +1490,10 @@ bool ManagerImpl::getConfigList(const std::string& sequenceId, const std::string& name) { bool returnValue = false; + TokenList tk; if (name=="codecdescriptor") { - TokenList tk; + CodecMap::iterator iter = _codecMap.begin(); - while( iter != _codecMap.end() ) { tk.clear(); std::ostringstream strType; @@ -1492,24 +1506,13 @@ ManagerImpl::getConfigList(const std::string& sequenceId, const std::string& nam returnValue = true; } else if (name=="ringtones") { std::string path = std::string(PROGSHAREDIR) + "/" + RINGDIR; - try { - ost::Dir dir(path.c_str()); - const char *cFileName = NULL; - std::string fileName; - std::string filePathName; - while ( (cFileName=dir++) != NULL ) { - fileName = cFileName; - filePathName = path + "/" + cFileName; - if (fileName.length() && fileName[0]!='.' && !ost::isDir(fileName.c_str())) { - _debug("Filename: %s\n", fileName.c_str()); - } - } - returnValue = true; - } catch (...) { - // error to open file dir - } - } else if (name=="") { - returnValue = true; + int nbFile = 0; + returnValue = getDirListing(sequenceId, path, &nbFile); + + path = std::string(HOMEDIR) + "/." + PROGNAME + "/" + RINGDIR; + getDirListing(sequenceId, path, &nbFile); + } else if (name=="audiodevice") { + returnValue = getAudioDeviceList(sequenceId); } else if (name=="") { returnValue = true; } else if (name=="") { @@ -1518,6 +1521,63 @@ ManagerImpl::getConfigList(const std::string& sequenceId, const std::string& nam return returnValue; } +/** + * User request Main Thread (list) + */ +bool +ManagerImpl::getAudioDeviceList(const std::string& sequenceId) +{ + TokenList tk; + portaudio::AutoSystem autoSys; + portaudio::System& sys = portaudio::System::instance(); + + const char *hostApiName; + const char *deviceName; + + for (int index = 0; index < sys.deviceCount(); index++ ) { + portaudio::Device& device = sys.deviceByIndex(index); + hostApiName = device.hostApi().name(); + deviceName = device.name(); + + tk.clear(); + std::ostringstream str; str << index; tk.push_back(str.str()); + tk.push_back(std::string(hostApiName) + " (device #" + str.str() + ")"); + _gui->sendMessage("100", sequenceId, tk); + } + return true; +} + +/** + * User action : main thread + */ +bool +ManagerImpl::getDirListing(const std::string& sequenceId, const std::string& path, int *nbFile) { + TokenList tk; + try { + ost::Dir dir(path.c_str()); + const char *cFileName = NULL; + std::string fileName; + std::string filePathName; + while ( (cFileName=dir++) != NULL ) { + fileName = cFileName; + filePathName = path + "/" + cFileName; + if (fileName.length() && fileName[0]!='.' && !ost::isDir(filePathName.c_str())) { + tk.clear(); + std::ostringstream str; + str << (*nbFile); + tk.push_back(str.str()); + tk.push_back(filePathName); + _gui->sendMessage("100", sequenceId, tk); + (*nbFile)++; + } + } + return true; + } catch (...) { + // error to open file dir + return false; + } +} + /** * Multi Thread */ diff --git a/src/managerimpl.h b/src/managerimpl.h index 3b0dff412a1915b8e8b400a3fc07b04261fa2e5f..853b9d720f1ada70c46b7d2c70a989f4cafa6802 100644 --- a/src/managerimpl.h +++ b/src/managerimpl.h @@ -191,7 +191,8 @@ public: // configuration function requests bool getZeroconf(const std::string& sequenceId); - bool attachZeroconfEvents(const std::string& sequenceId, const Pattern::Observer &observer); + bool attachZeroconfEvents(const std::string& sequenceId, Pattern::Observer& observer); + bool removeZeroconfEvents(Pattern::Observer& observer); bool getCallStatus(const std::string& sequenceId); bool getConfigAll(const std::string& sequenceId); bool getConfig(const std::string& section, const std::string& name, TokenList& arg); @@ -261,10 +262,11 @@ name); /* * Functions about audio device */ +/* AudioDevice deviceList (int); int deviceCount (void); bool defaultDevice (int); - +*/ /* * Init default values for the different fields */ @@ -314,6 +316,13 @@ private: */ void initVolume(); + /** + * Configuration + */ + bool getDirListing(const std::string& sequenceId, const std::string& path, int *nbFile); + bool getAudioDeviceList(const std::string& sequenceId); + Conf::ConfigTree _config; + /* * Play one tone * @return false if the driver is uninitialize @@ -394,13 +403,9 @@ private: // Variables used in exception bool _loaded; - // look if zeroconf scanning should run or not - int _useZeroconf; - // tell if we have zeroconf d'enable + // tell if we have zeroconf is enabled int _hasZeroconf; - Conf::ConfigTree _config; - void switchCall(short id); #ifdef USE_ZEROCONF diff --git a/src/zeroconf/DNSService.cpp b/src/zeroconf/DNSService.cpp index b5b5a80d45a9776b8688ed6baeae0c5a44e1297b..63df7c517afb4113c1e3a29b095575f387a32035 100644 --- a/src/zeroconf/DNSService.cpp +++ b/src/zeroconf/DNSService.cpp @@ -33,11 +33,12 @@ */ DNSService::DNSService() { + _start = false; _regtypeList.push_back("_sip._udp"); #ifdef USE_IAX2 _regtypeList.push_back("_iax._udp"); #endif - + // for the thread, the ifdef add a dynamic _regtypeList problem for (std::list<std::string>::iterator iterThread=_regtypeList.begin(); iterThread!=_regtypeList.end(); @@ -62,11 +63,12 @@ DNSService::~DNSService() * Look for zeroconf services and add them to _services */ void -DNSService::scanServices() +DNSService::startScanServices() { for (std::vector<DNSQueryThread *>::iterator iter = _queryThread.begin();iter!=_queryThread.end();iter++) { (*iter)->start(); } + _start = true; } /** @@ -81,6 +83,7 @@ void DNSService::addService(const std::string &service) // we leave before the queryService since, each // thread will modify a DNSServiceTXTRecord of a difference services _mutex.leaveMutex(); + notify(); queryService(service); } @@ -90,8 +93,10 @@ void DNSService::addService(const std::string &service) */ void DNSService::removeService(const std::string &service) { - ost::MutexLock(_mutex); + _mutex.enterMutex(); _services.erase(service); + _mutex.leaveMutex(); + notify(); } /** @@ -116,7 +121,7 @@ DNSService::listServices() DNSServiceMap DNSService::getServices() { - ost::MutexLock(_mutex); + ost::MutexLock m(_mutex); return _services; } @@ -192,9 +197,7 @@ DNSService::addTXTRecord(const char *fullname, uint16_t rdlen, const void *rdata } } - // TODO: remove this call, when we do not debug.. - // addTXTRecord is a good function to know changes... - listServices(); + notify(); } void diff --git a/src/zeroconf/DNSService.h b/src/zeroconf/DNSService.h index cd6b2f0bd85c8282461b834830a7289a37336efa..a721173686c3fff1b6283f7744576fecc9f9927d 100644 --- a/src/zeroconf/DNSService.h +++ b/src/zeroconf/DNSService.h @@ -38,7 +38,7 @@ public: DNSService(); ~DNSService(); - void scanServices(); // looking for services + void startScanServices(); // looking for services void addService(const std::string &service); // adding every services void removeService(const std::string &service); // remove a service void listServices(); // listing services (call addService before) @@ -50,6 +50,8 @@ public: void addTXTRecord(const char *fullname, uint16_t rdlen, const void *rdata); //void removeTXTRecord(const char *fullname); + bool isStart() const { return _start; } + private: DNSServiceMap _services; //map @@ -63,6 +65,8 @@ private: * It will be use to initialize the DNSQueryThread */ std::list<std::string> _regtypeList; + + bool _start; }; void DNSServiceAddServicesCallback(DNSServiceRef sdRef, diff --git a/src/zeroconf/INSTALL b/src/zeroconf/INSTALL index 85a836c46b76e2d9eda0fafdaadc60fe999891be..31bb0e60143e8e5c930f8c31e88b6cd425979351 100644 --- a/src/zeroconf/INSTALL +++ b/src/zeroconf/INSTALL @@ -9,6 +9,7 @@ Howl's one is named 'mDNSResponder'. - or you can get tarball from: http://helios.et.put.poznan.pl/~jstachow/pub/mDNSResponder-98.tar.gz (for those who don't like registration) - you can also use the last mDNSResponder + like http://helios.et.put.poznan.pl/~jstachow/pub/mDNSResponder-107.1.tar.gz 2) compile and install Build system for mDNSResponder is quite weird so here are instructions: