publicservice.cpp
00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021 #include "config.h"
00022
00023 #include "publicservice.h"
00024 #ifdef HAVE_SYS_TYPES_H
00025 #include <sys/types.h>
00026 #endif
00027 #include <netinet/in.h>
00028 #include <qapplication.h>
00029 #include "sdevent.h"
00030 #include "responder.h"
00031 #include "settings.h"
00032
00033 namespace DNSSD
00034 {
00035 #ifdef HAVE_DNSSD
00036 void publish_callback (DNSServiceRef, DNSServiceFlags, DNSServiceErrorType errorCode, const char *name,
00037 const char*, const char*, void *context);
00038 #endif
00039 class PublicServicePrivate : public Responder
00040 {
00041 public:
00042 PublicServicePrivate() : m_published(false)
00043 {}
00044 bool m_published;
00045 };
00046
00047 PublicService::PublicService(const QString& name, const QString& type, unsigned int port,
00048 const QString& domain)
00049 : QObject(), ServiceBase(name, type, QString::null, domain, port)
00050 {
00051 d = new PublicServicePrivate;
00052 if (domain.isNull())
00053 if (Configuration::publishType()==Configuration::EnumPublishType::LAN) m_domain="local.";
00054 else m_domain=Configuration::publishDomain();
00055 }
00056
00057
00058 PublicService::~PublicService()
00059 {
00060 stop();
00061 delete d;
00062 }
00063
00064 void PublicService::setServiceName(const QString& serviceName)
00065 {
00066 m_serviceName = serviceName;
00067 if (d->isRunning()) {
00068 stop();
00069 publishAsync();
00070 }
00071 }
00072
00073 void PublicService::setDomain(const QString& domain)
00074 {
00075 m_domain = domain;
00076 if (d->isRunning()) {
00077 stop();
00078 publishAsync();
00079 }
00080 }
00081
00082
00083 void PublicService::setType(const QString& type)
00084 {
00085 m_type = type;
00086 if (d->isRunning()) {
00087 stop();
00088 publishAsync();
00089 }
00090 }
00091
00092 void PublicService::setPort(unsigned short port)
00093 {
00094 m_port = port;
00095 if (d->isRunning()) {
00096 stop();
00097 publishAsync();
00098 }
00099 }
00100
00101 bool PublicService::isPublished() const
00102 {
00103 return d->m_published;
00104 }
00105
00106 void PublicService::setTextData(const QMap<QString,QString>& textData)
00107 {
00108 m_textData = textData;
00109 if (d->isRunning()) {
00110 stop();
00111 publishAsync();
00112 }
00113 }
00114
00115 bool PublicService::publish()
00116 {
00117 publishAsync();
00118 while (d->isRunning() && !d->m_published) d->process();
00119 return d->m_published;
00120 }
00121
00122 void PublicService::stop()
00123 {
00124 d->stop();
00125 d->m_published = false;
00126 }
00127
00128 void PublicService::publishAsync()
00129 {
00130 if (d->isRunning()) stop();
00131 #ifdef HAVE_DNSSD
00132 TXTRecordRef txt;
00133 TXTRecordCreate(&txt,0,0);
00134 QMap<QString,QString>::ConstIterator itEnd = m_textData.end();
00135 for (QMap<QString,QString>::ConstIterator it = m_textData.begin(); it!=itEnd ; ++it) {
00136 QCString value = it.data().utf8();
00137 if (TXTRecordSetValue(&txt,it.key().utf8(),value.length(),value)!=kDNSServiceErr_NoError) {
00138 TXTRecordDeallocate(&txt);
00139 emit published(false);
00140 return;
00141 }
00142 }
00143 DNSServiceRef ref;
00144 if (DNSServiceRegister(&ref,0,0,m_serviceName.utf8(),m_type.ascii(),domainToDNS(m_domain),NULL,
00145 htons(m_port),TXTRecordGetLength(&txt),TXTRecordGetBytesPtr(&txt),publish_callback,
00146 reinterpret_cast<void*>(this)) == kDNSServiceErr_NoError) d->setRef(ref);
00147 TXTRecordDeallocate(&txt);
00148 #endif
00149 if (!d->isRunning()) emit published(false);
00150 }
00151
00152 #ifdef HAVE_DNSSD
00153 void publish_callback (DNSServiceRef, DNSServiceFlags, DNSServiceErrorType errorCode, const char *name,
00154 const char*, const char*, void *context)
00155 {
00156 QObject *obj = reinterpret_cast<QObject*>(context);
00157 if (errorCode != kDNSServiceErr_NoError) {
00158 ErrorEvent err;
00159 QApplication::sendEvent(obj, &err);
00160 } else {
00161 PublishEvent pev(QString::fromUtf8(name));
00162 QApplication::sendEvent(obj, &pev);
00163 }
00164 }
00165 #endif
00166
00167
00168 void PublicService::customEvent(QCustomEvent* event)
00169 {
00170 if (event->type()==QEvent::User+SD_ERROR) {
00171 stop();
00172 emit published(false);
00173 }
00174 if (event->type()==QEvent::User+SD_PUBLISH) {
00175 d->m_published=true;
00176 emit published(true);
00177 m_serviceName = static_cast<PublishEvent*>(event)->m_name;
00178 }
00179 }
00180
00181 void PublicService::virtual_hook(int, void*)
00182 {
00183 }
00184
00185 }
00186
00187 #include "publicservice.moc"
This file is part of the documentation for dnssd Library Version 3.4.0.