00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033 #include "TBonjourBrowser.h"
00034 #include "TBonjourRecord.h"
00035 #include "TSysEvtHandler.h"
00036 #include "TList.h"
00037 #include "TError.h"
00038 #include "TSystem.h"
00039
00040
00041 ClassImp(TBonjourBrowser)
00042
00043
00044 TBonjourBrowser::TBonjourBrowser() : fDNSRef(0), fBonjourSocketHandler(0)
00045 {
00046
00047
00048 fBonjourRecords = new TList;
00049 fBonjourRecords->SetOwner();
00050
00051
00052 gSystem->Setenv("AVAHI_COMPAT_NOWARN", "1");
00053 }
00054
00055
00056 TBonjourBrowser::~TBonjourBrowser()
00057 {
00058
00059
00060 delete fBonjourRecords;
00061 delete fBonjourSocketHandler;
00062
00063 if (fDNSRef) {
00064 DNSServiceRefDeallocate(fDNSRef);
00065 fDNSRef = 0;
00066 }
00067 }
00068
00069
00070 Int_t TBonjourBrowser::BrowseForServiceType(const char *serviceType)
00071 {
00072
00073
00074
00075 DNSServiceErrorType err = DNSServiceBrowse(&fDNSRef, 0,
00076 0, serviceType, 0,
00077 (DNSServiceBrowseReply)BonjourBrowseReply,
00078 this);
00079 if (err != kDNSServiceErr_NoError) {
00080 Error("BrowseForServiceType", "error in DNSServiceBrowse (%d)", err);
00081 return -1;
00082 }
00083
00084 Int_t sockfd = DNSServiceRefSockFD(fDNSRef);
00085 if (sockfd == -1) {
00086 Error("BrowseForServiceType", "invalid sockfd");
00087 return -1;
00088 }
00089
00090 fBonjourSocketHandler = new TFileHandler(sockfd, TFileHandler::kRead);
00091 fBonjourSocketHandler->Connect("Notified()", "TBonjourBrowser", this, "BonjourSocketReadyRead()");
00092 fBonjourSocketHandler->Add();
00093
00094 return 0;
00095 }
00096
00097
00098 void TBonjourBrowser::CurrentBonjourRecordsChanged(TList *bonjourRecords)
00099 {
00100
00101
00102 Emit("CurrentBonjourRecordsChanged(TList*)", (Long_t)bonjourRecords);
00103 }
00104
00105
00106 void TBonjourBrowser::BonjourSocketReadyRead()
00107 {
00108
00109
00110
00111
00112
00113 if (!fDNSRef) return;
00114
00115 DNSServiceErrorType err = DNSServiceProcessResult(fDNSRef);
00116 if (err != kDNSServiceErr_NoError)
00117 Error("BonjourSocketReadyRead", "error in DNSServiceProcessResult");
00118 }
00119
00120
00121 void TBonjourBrowser::BonjourBrowseReply(DNSServiceRef,
00122 DNSServiceFlags flags, UInt_t,
00123 DNSServiceErrorType errorCode,
00124 const char *serviceName, const char *regType,
00125 const char *replyDomain, void *context)
00126 {
00127
00128
00129 TBonjourBrowser *browser = static_cast<TBonjourBrowser*>(context);
00130 if (errorCode != kDNSServiceErr_NoError) {
00131 ::Error("TBonjourBrowser::BonjourBrowseReply", "error in BonjourBrowseReply");
00132
00133 } else {
00134 TBonjourRecord *record = new TBonjourRecord(serviceName, regType, replyDomain);
00135 if (flags & kDNSServiceFlagsAdd) {
00136 if (!browser->fBonjourRecords->FindObject(record))
00137 browser->fBonjourRecords->Add(record);
00138 else
00139 delete record;
00140 } else {
00141 TBonjourRecord *r = (TBonjourRecord*)browser->fBonjourRecords->Remove(record);
00142 delete r;
00143 delete record;
00144 }
00145 if (!(flags & kDNSServiceFlagsMoreComing)) {
00146 browser->CurrentBonjourRecordsChanged(browser->fBonjourRecords);
00147 }
00148 }
00149 }