⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 zone.java

📁 DNS Java 是java实现的DNS
💻 JAVA
字号:
// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)package org.xbill.DNS;import java.io.*;import java.util.*;/** * A DNS Zone.  This encapsulates all data related to a Zone, and provides * convenient lookup methods. * * @author Brian Wellington */public class Zone {/** A primary zone */public static final int PRIMARY = 1;/** A secondary zone */public static final int SECONDARY = 2;private Map data;private int type;private Name origin;private Object originNode;private int dclass = DClass.IN;private RRset NS;private SOARecord SOA;private boolean hasWild;class ZoneIterator implements Iterator {	private Iterator zentries;	private RRset [] current;	private int count;	private boolean wantLastSOA;	ZoneIterator(boolean axfr) {		zentries = data.entrySet().iterator();		wantLastSOA = axfr;		RRset [] sets = allRRsets(originNode);		current = new RRset[sets.length];		for (int i = 0, j = 2; i < sets.length; i++) {			int type = sets[i].getType();			if (type == Type.SOA)				current[0] = sets[i];			else if (type == Type.NS)				current[1] = sets[i];			else				current[j++] = sets[i];		}	}	public boolean	hasNext() {		return (current != null || wantLastSOA);	}	public Object	next() {		if (!hasNext()) {			throw new NoSuchElementException();		}		if (current == null && wantLastSOA) {			wantLastSOA = false;			return oneRRset(originNode, Type.SOA);		}		Object set = current[count++];		if (count == current.length) {			current = null;			while (zentries.hasNext()) {				Map.Entry entry = (Map.Entry) zentries.next();				if (entry.getKey().equals(origin))					continue;				RRset [] sets = allRRsets(entry.getValue());				if (sets.length == 0)					continue;				current = sets;				count = 0;				break;			}		}		return set;	}	public void	remove() {		throw new UnsupportedOperationException();	}}private voidvalidate() throws IOException {	originNode = exactName(origin);	if (originNode == null)		throw new IOException(origin + ": no data specified");	RRset rrset = oneRRset(originNode, Type.SOA);	if (rrset == null || rrset.size() != 1)		throw new IOException(origin +				      ": exactly 1 SOA must be specified");	Iterator it = rrset.rrs();	SOA = (SOARecord) it.next();	NS = oneRRset(originNode, Type.NS);	if (NS == null)		throw new IOException(origin + ": no NS set specified");}private final voidmaybeAddRecord(Record record) throws IOException {	int rtype = record.getType();	Name name = record.getName();	if (rtype == Type.SOA && !name.equals(origin)) {		throw new IOException("SOA owner " + name +				      " does not match zone origin " +				      origin);	}	if (name.subdomain(origin))		addRecord(record);}/** * Creates a Zone from the records in the specified master file. * @param zone The name of the zone. * @param file The master file to read from. * @see Master */publicZone(Name zone, String file) throws IOException {	data = new HashMap();	type = PRIMARY;	if (zone == null)		throw new IllegalArgumentException("no zone name specified");	Master m = new Master(file, zone);	Record record;	origin = zone;	while ((record = m.nextRecord()) != null)		maybeAddRecord(record);	validate();}/** * Creates a Zone from an array of records. * @param zone The name of the zone. * @param records The records to add to the zone. * @see Master */publicZone(Name zone, Record [] records) throws IOException {	data = new HashMap();	type = PRIMARY;	if (zone == null)		throw new IllegalArgumentException("no zone name specified");	origin = zone;	for (int i = 0; i < records.length; i++)		maybeAddRecord(records[i]);	validate();}private voidfromXFR(ZoneTransferIn xfrin) throws IOException, ZoneTransferException {	data = new HashMap();	type = SECONDARY;	if (!xfrin.isAXFR())		throw new IllegalArgumentException("zones can only be " +						   "created from AXFRs");	origin = xfrin.getName();	List records = xfrin.run();	for (Iterator it = records.iterator(); it.hasNext(); ) {		Record record = (Record) it.next();		maybeAddRecord(record);	}	validate();}/** * Creates a Zone by doing the specified zone transfer. * @param xfrin The incoming zone transfer to execute. * @see ZoneTransferIn */publicZone(ZoneTransferIn xfrin) throws IOException, ZoneTransferException {	fromXFR(xfrin);}/** * Creates a Zone by performing a zone transfer to the specified host. * @see ZoneTransferIn */publicZone(Name zone, int dclass, String remote)throws IOException, ZoneTransferException{	ZoneTransferIn xfrin = ZoneTransferIn.newAXFR(zone, remote, null);	xfrin.setDClass(dclass);	fromXFR(xfrin);}/** Returns the Zone's origin */public NamegetOrigin() {	return origin;}/** Returns the Zone origin's NS records */public RRsetgetNS() {	return NS;}/** Returns the Zone's SOA record */public SOARecordgetSOA() {	return SOA;}/** Returns the Zone's class */public intgetDClass() {	return dclass;}private synchronized ObjectexactName(Name name) {	return data.get(name);}private synchronized RRset []allRRsets(Object types) {	if (types instanceof List) {		List typelist = (List) types;		return (RRset []) typelist.toArray(new RRset[typelist.size()]);	} else {		RRset set = (RRset) types;		return new RRset [] {set};	}}private synchronized RRsetoneRRset(Object types, int type) {	if (type == Type.ANY)		throw new IllegalArgumentException("oneRRset(ANY)");	if (types instanceof List) {		List list = (List) types;		for (int i = 0; i < list.size(); i++) {			RRset set = (RRset) list.get(i);			if (set.getType() == type)				return set;		}	} else {		RRset set = (RRset) types;		if (set.getType() == type)			return set;	}	return null;}private synchronized RRsetfindRRset(Name name, int type) {	Object types = exactName(name);	if (types == null)		return null;	return oneRRset(types, type);}private synchronized voidaddRRset(Name name, RRset rrset) {	if (!hasWild && name.isWild())		hasWild = true;	Object types = data.get(name);	if (types == null) {		data.put(name, rrset);		return;	}	int rtype = rrset.getType();	if (types instanceof List) {		List list = (List) types;		for (int i = 0; i < list.size(); i++) {			RRset set = (RRset) list.get(i);			if (set.getType() == rtype) {				list.set(i, rrset);				return;			}		}		list.add(rrset);	} else {		RRset set = (RRset) types;		if (set.getType() == rtype)			data.put(name, rrset);		else {			LinkedList list = new LinkedList();			list.add(set);			list.add(rrset);			data.put(name, list);		}	}}private synchronized voidremoveRRset(Name name, int type) {	Object types = data.get(name);	if (types == null) {		return;	}	if (types instanceof List) {		List list = (List) types;		for (int i = 0; i < list.size(); i++) {			RRset set = (RRset) list.get(i);			if (set.getType() == type) {				list.remove(i);				if (list.size() == 0)					data.remove(name);				return;			}		}	} else {		RRset set = (RRset) types;		if (set.getType() != type)			return;		data.remove(name);	}}private synchronized SetResponselookup(Name name, int type) {	int labels;	int olabels;	int tlabels;	RRset rrset;	Name tname;	Object types;	SetResponse sr;	if (!name.subdomain(origin))		return SetResponse.ofType(SetResponse.NXDOMAIN);	labels = name.labels();	olabels = origin.labels();	for (tlabels = olabels; tlabels <= labels; tlabels++) {		boolean isOrigin = (tlabels == olabels);		boolean isExact = (tlabels == labels);		if (isOrigin)			tname = origin;		else if (isExact)			tname = name;		else			tname = new Name(name, labels - tlabels);		types = exactName(tname);		if (types == null)			continue;		/* If this is a delegation, return that. */		if (!isOrigin) {			RRset ns = oneRRset(types, Type.NS);			if (ns != null)				return new SetResponse(SetResponse.DELEGATION,						       ns);		}		/* If this is an ANY lookup, return everything. */		if (isExact && type == Type.ANY) {			sr = new SetResponse(SetResponse.SUCCESSFUL);			RRset [] sets = allRRsets(types);			for (int i = 0; i < sets.length; i++)				sr.addRRset(sets[i]);			return sr;		}		/*		 * If this is the name, look for the actual type or a CNAME.		 * Otherwise, look for a DNAME.		 */		if (isExact) {			rrset = oneRRset(types, type);			if (rrset != null) {				sr = new SetResponse(SetResponse.SUCCESSFUL);				sr.addRRset(rrset);				return sr;			}			rrset = oneRRset(types, Type.CNAME);			if (rrset != null)				return new SetResponse(SetResponse.CNAME,						       rrset);		} else {			rrset = oneRRset(types, Type.DNAME);			if (rrset != null)				return new SetResponse(SetResponse.DNAME,						       rrset);		}		/* We found the name, but not the type. */		if (isExact)			return SetResponse.ofType(SetResponse.NXRRSET);	}	if (hasWild) {		for (int i = 0; i < labels - olabels; i++) {			tname = name.wild(i + 1);			types = exactName(tname);			if (types == null)				continue;			rrset = oneRRset(types, type);			if (rrset != null) {				sr = new SetResponse(SetResponse.SUCCESSFUL);				sr.addRRset(rrset);				return sr;			}		}	}	return SetResponse.ofType(SetResponse.NXDOMAIN);}/**      * Looks up Records in the Zone.  This follows CNAMEs and wildcards. * @param name The name to look up * @param type The type to look up * @return A SetResponse object * @see SetResponse */ public SetResponsefindRecords(Name name, int type) {	return lookup(name, type);}/** * Looks up Records in the zone, finding exact matches only. * @param name The name to look up * @param type The type to look up * @return The matching RRset * @see RRset */ public RRsetfindExactMatch(Name name, int type) {	Object types = exactName(name);	if (types == null)		return null;	return oneRRset(types, type);}/** * Adds an RRset to the Zone * @param rrset The RRset to be added * @see RRset */public voidaddRRset(RRset rrset) {	Name name = rrset.getName();	addRRset(name, rrset);}/** * Adds a Record to the Zone * @param r The record to be added * @see Record */public voidaddRecord(Record r) {	Name name = r.getName();	int rtype = r.getRRsetType();	synchronized (this) {		RRset rrset = findRRset(name, rtype);		if (rrset == null) {			rrset = new RRset(r);			addRRset(name, rrset);		} else {			rrset.addRR(r);		}	}}/** * Removes a record from the Zone * @param r The record to be removed * @see Record */public voidremoveRecord(Record r) {	Name name = r.getName();	int rtype = r.getRRsetType();	synchronized (this) {		RRset rrset = findRRset(name, rtype);		if (rrset == null)			return;		rrset.deleteRR(r);		if (rrset.size() == 0)			removeRRset(name, rtype);	}}/** * Returns an Iterator over the RRsets in the zone. */public Iteratoriterator() {	return new ZoneIterator(false);}/** * Returns an Iterator over the RRsets in the zone that can be used to * construct an AXFR response.  This is identical to {@link #iterator} except * that the SOA is returned at the end as well as the beginning. */public IteratorAXFR() {	return new ZoneIterator(true);}private voidnodeToString(StringBuffer sb, Object node) {	RRset [] sets = allRRsets(node);	for (int i = 0; i < sets.length; i++) {		RRset rrset = sets[i];		Iterator it = rrset.rrs();		while (it.hasNext())			sb.append(it.next() + "\n");		it = rrset.sigs();		while (it.hasNext())			sb.append(it.next() + "\n");	}}/** * Returns the contents of the Zone in master file format. */public StringtoMasterFile() {	Iterator zentries = data.entrySet().iterator();	StringBuffer sb = new StringBuffer();	nodeToString(sb, originNode);	while (zentries.hasNext()) {		Map.Entry entry = (Map.Entry) zentries.next();		if (!origin.equals(entry.getKey()))			nodeToString(sb, entry.getValue());	}	return sb.toString();}/** * Returns the contents of the Zone as a string (in master file format). */public StringtoString() {	return toMasterFile();}}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -