Skip to main content
aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMarkus Alexander Kuppe2010-06-10 09:42:52 +0000
committerMarkus Alexander Kuppe2010-06-10 09:42:52 +0000
commit492b00ab1ec907a83a32a7cace0375057cea7c84 (patch)
tree01444e27c7472a51c2105fb0d711cdd509e851dd
parentcebbdc4110d6f558d41fb6001c93658bf8702967 (diff)
downloadorg.eclipse.ecf-492b00ab1ec907a83a32a7cace0375057cea7c84.tar.gz
org.eclipse.ecf-492b00ab1ec907a83a32a7cace0375057cea7c84.tar.xz
org.eclipse.ecf-492b00ab1ec907a83a32a7cace0375057cea7c84.zip
NEW - bug 315970: [Discovery][DNS-SD] Discovery of Browsing and Registration Domains (Domain Enumeration)
https://bugs.eclipse.org/bugs/show_bug.cgi?id=315970
-rw-r--r--providers/bundles/org.eclipse.ecf.provider.dnssd/.gitignore1
-rw-r--r--providers/bundles/org.eclipse.ecf.provider.dnssd/src/org/eclipse/ecf/provider/dnssd/BnRDnsSdServiceTypeID.java74
-rw-r--r--providers/bundles/org.eclipse.ecf.provider.dnssd/src/org/eclipse/ecf/provider/dnssd/DnsSdDisocoveryLocator.java75
-rw-r--r--providers/bundles/org.eclipse.ecf.provider.dnssd/src/org/eclipse/ecf/provider/dnssd/DnsSdServiceTypeID.java70
4 files changed, 172 insertions, 48 deletions
diff --git a/providers/bundles/org.eclipse.ecf.provider.dnssd/.gitignore b/providers/bundles/org.eclipse.ecf.provider.dnssd/.gitignore
new file mode 100644
index 000000000..6dd29b7f8
--- /dev/null
+++ b/providers/bundles/org.eclipse.ecf.provider.dnssd/.gitignore
@@ -0,0 +1 @@
+bin/ \ No newline at end of file
diff --git a/providers/bundles/org.eclipse.ecf.provider.dnssd/src/org/eclipse/ecf/provider/dnssd/BnRDnsSdServiceTypeID.java b/providers/bundles/org.eclipse.ecf.provider.dnssd/src/org/eclipse/ecf/provider/dnssd/BnRDnsSdServiceTypeID.java
new file mode 100644
index 000000000..4a8cb3d6e
--- /dev/null
+++ b/providers/bundles/org.eclipse.ecf.provider.dnssd/src/org/eclipse/ecf/provider/dnssd/BnRDnsSdServiceTypeID.java
@@ -0,0 +1,74 @@
+/*******************************************************************************
+ * Copyright (c) 2010 Markus Alexander Kuppe.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Markus Alexander Kuppe (ecf-dev_eclipse.org <at> lemmster <dot> de) - initial API and implementation
+ ******************************************************************************/
+package org.eclipse.ecf.provider.dnssd;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.eclipse.ecf.discovery.identity.IServiceTypeID;
+import org.xbill.DNS.Lookup;
+import org.xbill.DNS.TextParseException;
+import org.xbill.DNS.Type;
+
+/**
+ * This ServiceType represents the special RRs defined in
+ * chapter 12. Discovery of Browsing and Registration Domains
+ *
+ * @see http://files.dns-sd.org/draft-cheshire-dnsext-dns-sd.txt
+ */
+public class BnRDnsSdServiceTypeID extends DnsSdServiceTypeID {
+ private static final long serialVersionUID = -466458565598238072L;
+
+ /**
+ * A list of domains recommended for browsing
+ */
+ static final String BROWSE_DOMAIN = "b._dns-sd";
+ /**
+ * A single recommended default domain for browsing
+ */
+ static final String DEFAULT_BROWSE_DOMAIN = "db._dns-sd";
+ /**
+ * A list of domains recommended for registering services using Dynamic Update
+ */
+ static final String REG_DOMAIN = "r._dns-sd";
+ /**
+ * A single recommended default domain for registering services.
+ */
+ static final String DEFAULT_REG_DOMAIN = "dr._dns-sd";
+
+ BnRDnsSdServiceTypeID(IServiceTypeID aServiceType, String aService) {
+ super(aServiceType.getNamespace(), aServiceType);
+ services = new String[] {aService};
+ }
+
+ /* (non-Javadoc)
+ * @see org.eclipse.ecf.provider.dnssd.DnsSdServiceTypeID#getInternalQueries()
+ */
+ Lookup[] getInternalQueries() {
+ List result = new ArrayList();
+ for (int i = 0; i < scopes.length; i++) {
+ String scope = scopes[i];
+ // remove dangling "."
+ if(scope.endsWith(".")) {
+ scope = scope.substring(0, scope.length() - 1);
+ }
+ Lookup query;
+ try {
+ query = new Lookup(services[0] + "._udp" + "." + scope + ".",
+ Type.PTR);
+ } catch (TextParseException e) {
+ continue;
+ }
+ result.add(query);
+ }
+ return (Lookup[]) result.toArray(new Lookup[result.size()]);
+ }
+}
diff --git a/providers/bundles/org.eclipse.ecf.provider.dnssd/src/org/eclipse/ecf/provider/dnssd/DnsSdDisocoveryLocator.java b/providers/bundles/org.eclipse.ecf.provider.dnssd/src/org/eclipse/ecf/provider/dnssd/DnsSdDisocoveryLocator.java
index 69e78b0f8..bb4a3e07c 100644
--- a/providers/bundles/org.eclipse.ecf.provider.dnssd/src/org/eclipse/ecf/provider/dnssd/DnsSdDisocoveryLocator.java
+++ b/providers/bundles/org.eclipse.ecf.provider.dnssd/src/org/eclipse/ecf/provider/dnssd/DnsSdDisocoveryLocator.java
@@ -14,9 +14,11 @@ import java.net.URI;
import java.net.UnknownHostException;
import java.util.ArrayList;
import java.util.Arrays;
+import java.util.HashSet;
import java.util.Iterator;
import java.util.List;
import java.util.Properties;
+import java.util.Set;
import org.eclipse.core.runtime.Assert;
import org.eclipse.ecf.core.ContainerConnectException;
@@ -86,27 +88,38 @@ public class DnsSdDisocoveryLocator extends AbstractDiscoveryContainerAdapter {
*/
public IServiceTypeID[] getServiceTypes() {
// technically can't do anything without a scope (domain) -> falling back to local domain (mDNS?)
- List result = new ArrayList();
DnsSdServiceTypeID serviceTypeId = (DnsSdServiceTypeID) targetID;
+ return getServiceTypes(serviceTypeId);
+ }
+
+ private IServiceTypeID[] getServiceTypes(final DnsSdServiceTypeID serviceTypeId) {
+ List result = new ArrayList();
+ Record[] queryResult = getRecords(serviceTypeId);
+ for (int j = 0; j < queryResult.length; j++) {
+ Record record = queryResult[j];
+ if(record instanceof PTRRecord) {
+ PTRRecord ptrRecord = (PTRRecord) record;
+ result.add(new DnsSdServiceTypeID(getServicesNamespace(), ptrRecord.getTarget()));
+ } else if (record instanceof SRVRecord) {
+ SRVRecord srvRecord = (SRVRecord) record;
+ result.add(new DnsSdServiceTypeID(getServicesNamespace(), srvRecord.getName()));
+ }
+ }
+ return (IServiceTypeID[]) result.toArray(new IServiceTypeID[result.size()]);
+ }
+
+ private Record[] getRecords(final DnsSdServiceTypeID serviceTypeId) {
+ List result = new ArrayList();
Lookup[] queries = serviceTypeId.getInternalQueries();
for (int i = 0; i < queries.length; i++) {
Lookup query = queries[i];
query.setResolver(resolver);
Record[] queryResult = query.run();
- //TODO file bug upstream that queryResult may never be null
- int length = queryResult == null ? 0 : queryResult.length;
- for (int j = 0; j < length; j++) {
- Record record = queryResult[j];
- if(record instanceof PTRRecord) {
- PTRRecord ptrRecord = (PTRRecord) record;
- result.add(new DnsSdServiceTypeID(getServicesNamespace(), ptrRecord.getTarget()));
- } else if (record instanceof SRVRecord) {
- SRVRecord srvRecord = (SRVRecord) record;
- result.add(new DnsSdServiceTypeID(getServicesNamespace(), srvRecord.getName()));
- }
+ if(queryResult != null) {
+ result.addAll(Arrays.asList(queryResult));
}
}
- return (IServiceTypeID[]) result.toArray(new IServiceTypeID[result.size()]);
+ return (Record[]) result.toArray(new Record[result.size()]);
}
/*
@@ -236,32 +249,60 @@ public class DnsSdDisocoveryLocator extends AbstractDiscoveryContainerAdapter {
*/
public void connect(ID aTargetID, IConnectContext connectContext)
throws ContainerConnectException {
+
+ // connect can only be called once
if (targetID != null || getConfig() == null) {
throw new ContainerConnectException("Already connected");
}
+
+ // fall back to the search path as last resort
if(aTargetID == null || !(aTargetID instanceof DnsSdServiceTypeID)) {
- // fall back to the search path as last resort
ResolverConfig config = new ResolverConfig();
Name[] searchPaths = config.searchPath();
if(searchPaths.length >= 0) {
targetID = new DnsSdServiceTypeID();
- targetID.setScopes(searchPaths);
+ targetID.setSearchPath(searchPaths);
} else {
throw new ContainerConnectException("No target id given");
}
} else {
targetID = (DnsSdServiceTypeID) aTargetID;
}
+
+ // instantiate a default resolver
try {
resolver = new SimpleResolver();
} catch (UnknownHostException e) {
throw new ContainerConnectException(e);
}
- fireContainerEvent(new ContainerConnectingEvent(this.getID(), targetID,
+
+ // read browsing domains for the given targetID/searchpath and merge with existing
+ targetID.addSearchPath(getBrowsingDomains(targetID));
+
+ // done setting up this provider, send event
+ fireContainerEvent(new ContainerConnectingEvent(this.getID(), targetID,
connectContext));
fireContainerEvent(new ContainerConnectedEvent(this.getID(), targetID));
}
+ private String[] getBrowsingDomains(IServiceTypeID aServiceTypeId) {
+ Set res = new HashSet();
+
+ String[] rrs = new String[] {BnRDnsSdServiceTypeID.BROWSE_DOMAIN, BnRDnsSdServiceTypeID.DEFAULT_BROWSE_DOMAIN};
+ for (int i = 0; i < rrs.length; i++) {
+ BnRDnsSdServiceTypeID serviceType =
+ new BnRDnsSdServiceTypeID(aServiceTypeId, rrs[i]);
+
+ Record[] defaultBrowsing = getRecords(serviceType);
+ for (int j = 0; j < defaultBrowsing.length; j++) {
+ PTRRecord record = (PTRRecord) defaultBrowsing[j];
+ res.add(record.getTarget().toString());
+ }
+ }
+
+ return (String[]) res.toArray(new String[res.size()]);
+ }
+
/*
* (non-Javadoc)
*
@@ -288,7 +329,7 @@ public class DnsSdDisocoveryLocator extends AbstractDiscoveryContainerAdapter {
* @param searchPaths The default search path used for discovery
*/
public void setSearchPath(String[] searchPaths) {
- targetID.setScopes(searchPaths);
+ targetID.setSearchPath(searchPaths);
}
/**
diff --git a/providers/bundles/org.eclipse.ecf.provider.dnssd/src/org/eclipse/ecf/provider/dnssd/DnsSdServiceTypeID.java b/providers/bundles/org.eclipse.ecf.provider.dnssd/src/org/eclipse/ecf/provider/dnssd/DnsSdServiceTypeID.java
index 4db8e2527..1ae3ad1c7 100644
--- a/providers/bundles/org.eclipse.ecf.provider.dnssd/src/org/eclipse/ecf/provider/dnssd/DnsSdServiceTypeID.java
+++ b/providers/bundles/org.eclipse.ecf.provider.dnssd/src/org/eclipse/ecf/provider/dnssd/DnsSdServiceTypeID.java
@@ -10,10 +10,12 @@
******************************************************************************/
package org.eclipse.ecf.provider.dnssd;
-import java.net.InetAddress;
-import java.net.UnknownHostException;
import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collection;
+import java.util.HashSet;
import java.util.List;
+import java.util.Set;
import org.eclipse.ecf.core.identity.IDCreateException;
import org.eclipse.ecf.core.identity.Namespace;
@@ -27,6 +29,14 @@ import org.xbill.DNS.Type;
public class DnsSdServiceTypeID extends ServiceTypeID implements IServiceTypeID {
private static final long serialVersionUID = 1247933069737880365L;
+
+ DnsSdServiceTypeID() {
+ super(new DnsSdNamespace());
+ scopes = DEFAULT_SCOPE;
+ protocols = DEFAULT_PROTO;
+ namingAuthority = DEFAULT_NA;
+ services = new String[]{""};
+ }
public DnsSdServiceTypeID(Namespace ns, IServiceTypeID id) {
super(ns, id);
@@ -36,32 +46,7 @@ public class DnsSdServiceTypeID extends ServiceTypeID implements IServiceTypeID
throws IDCreateException {
super(namespace, aType);
}
-
- public DnsSdServiceTypeID(Namespace namespace, String[] services,
- String[] scopes, String[] protocols, String namingAuthority) {
- super(namespace, services, scopes, protocols, namingAuthority);
- }
-
- public DnsSdServiceTypeID(Namespace namespace) {
- super(namespace);
- try {
- final InetAddress localHost = InetAddress.getLocalHost();
- final String fqdn = localHost.getCanonicalHostName();
- int idx = fqdn.indexOf(".");
- if(idx > -1) {
- scopes = new String[]{fqdn.substring(idx +1)};
- } else {
- scopes = new String[]{fqdn};
- }
- } catch (UnknownHostException e) {
- scopes = null;
- }
- }
- DnsSdServiceTypeID() {
- super(new DnsSdNamespace());
- }
-
DnsSdServiceTypeID(Namespace namespace, Name aName) {
super(namespace, aName.toString());
}
@@ -110,22 +95,45 @@ public class DnsSdServiceTypeID extends ServiceTypeID implements IServiceTypeID
return (Lookup[]) result.toArray(new Lookup[result.size()]);
}
- public void setScopes(Name[] searchPaths) {
+ /**
+ * @param searchPaths Sets the default search path
+ */
+ void setSearchPath(Name[] searchPaths) {
String[] s = new String[searchPaths.length];
for(int i = 0; i < searchPaths.length; i++) {
s[i] = searchPaths[i].toString();
}
- setScopes(s);
+ setSearchPath(s);
}
- public void setScopes(String[] searchPaths) {
+ /**
+ * @param searchPaths Sets the default search path
+ */
+ void setSearchPath(String[] searchPaths) {
scopes = searchPaths;
}
/**
* @return Search scopes used during discovery
*/
- public String[] getSearchPath() {
+ String[] getSearchPath() {
return scopes;
}
+
+ /**
+ * @param additionalSearchPaths Adds the given array to the existing search paths
+ */
+ void addSearchPath(String[] additionalSearchPaths) {
+ //convert arrays to collections (lists)
+ Collection coll1 = Arrays.asList(scopes);
+ Collection coll2 = Arrays.asList(additionalSearchPaths);
+
+ // remove dupes
+ Set s = new HashSet();
+ s.addAll(coll1);
+ s.addAll(coll2);
+
+ // convert into new scopes
+ scopes = (String[]) s.toArray(new String[s.size()]);
+ }
}

Back to the top