Skip to content

Commit

Permalink
domain hunter v0.9
Browse files Browse the repository at this point in the history
domain hunter v0.9:
update logic of getting possible https URLs that may contain related-domains
  • Loading branch information
bit4woo committed Sep 20, 2018
1 parent 6a057ff commit 12022db
Show file tree
Hide file tree
Showing 3 changed files with 65 additions and 26 deletions.
80 changes: 60 additions & 20 deletions src/burp/BurpExtender.java
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,7 @@ public class BurpExtender implements IBurpExtender, ITab, IContextMenuFactory

private PrintWriter stdout;//现在这里定义变量,再在registerExtenderCallbacks函数中实例化,如果都在函数中就只是局部变量,不能在这实例化,因为要用到其他参数。
private PrintWriter stderr;
private String ExtenderName = "Domain Hunter v0.7 by bit4";
private String ExtenderName = "Domain Hunter v0.9 by bit4";
private String github = "https://github.com/bit4woo/domain_hunter";
private Set<String> subdomainofset = new HashSet<String>();
private Set<String> domainlikeset = new HashSet<String>();
Expand Down Expand Up @@ -83,56 +83,64 @@ public void registerExtenderCallbacks(IBurpExtenderCallbacks callbacks)

}

public Map search(String subdomainof, String domainlike){
public Map<String, Set<String>> search(String subdomainof, String domainlike){
subdomainofset.clear();
domainlikeset.clear();
relatedDomainSet.clear();


if (!subdomainof.contains(".")||subdomainof.endsWith(".")||subdomainof.equals("")){
//如果域名为空,或者(不包含.号,或者点号在末尾的)
}else {
if (subdomainof.contains(".")&&!subdomainof.endsWith(".")&&!subdomainof.startsWith("."))
{
Set<String> httpsURLs = new HashSet<String>();
IHttpRequestResponse[] requestResponses = callbacks.getSiteMap(null);
//stdout.println(response[1]);
for (IHttpRequestResponse x:requestResponses){

IHttpService httpservice = x.getHttpService();
String shortURL = httpservice.toString();
String protocol = httpservice.getProtocol();
String Host = httpservice.getHost();

//stdout.println(url);
//stdout.println(shortURL);
//stdout.println(Host);

if (Host.endsWith("."+subdomainof)){
subdomainofset.add(Host);
//stdout.println(subdomainofset);

//get SANs info to get related domain, only when the [subdomain] is using https.
if(httpservice.getProtocol().equalsIgnoreCase("https")) {
if(protocol.equalsIgnoreCase("https")) {
httpsURLs.add(shortURL);
}
continue;
}


else if (domainlike.equals("")){

}
else if (Host.contains(domainlike) && !Host.equalsIgnoreCase(subdomainof)){
if (!domainlike.equals("") && Host.contains(domainlike) && !Host.equalsIgnoreCase(subdomainof)){
domainlikeset.add(Host);
if(protocol.equalsIgnoreCase("https")) {
httpsURLs.add(shortURL);
}
//stdout.println(domainlikeset);
continue;
}

if (validIP(Host)) {//https://202.77.129.30
if(protocol.equalsIgnoreCase("https")) {
httpsURLs.add(shortURL);
}
}
}

stdout.println("sub-domains and similar-domains search finished\n");
stdout.println("sub-domains and similar-domains search finished,starting get related-domains\n");
//stdout.println(httpsURLs);

//多线程获取
//Set<Future<Set<String>>> set = new HashSet<Future<Set<String>>>();
Map<String,Future<Set<String>>> urlResultmap = new HashMap<String,Future<Set<String>>>();
ExecutorService pool = Executors.newFixedThreadPool(10);

for (String url:httpsURLs) {
Callable<Set<String>> callable = new ThreadCertInfo(url,subdomainof);
Callable<Set<String>> callable = new ThreadCertInfo(url,domainlike);
Future<Set<String>> future = pool.submit(callable);
//set.add(future);
urlResultmap.put(url, future);
Expand Down Expand Up @@ -179,7 +187,7 @@ else if (Host.contains(domainlike) && !Host.equalsIgnoreCase(subdomainof)){
for (String item:tmpRelatedDomainSet) {
if (item.endsWith("."+subdomainof)){
subdomainofset.add(item);
}else if (item.contains(domainlike) && !item.equalsIgnoreCase(subdomainof)){
}else if (!domainlike.equals("") && item.contains(domainlike) && !item.equalsIgnoreCase(subdomainof)){
domainlikeset.add(item);
}else {
relatedDomainSet.add(item);
Expand All @@ -188,15 +196,15 @@ else if (Host.contains(domainlike) && !Host.equalsIgnoreCase(subdomainof)){

}

Map result = new HashMap();
Map<String, Set<String>> result = new HashMap<String, Set<String>>();
result.put("subdomainofset", subdomainofset);
result.put("domainlikeset", domainlikeset);
result.put("relatedDomainSet", relatedDomainSet);
return result;

}

public Map spiderall (String subdomainof, String domainlike) {
public Map<String, Set<String>> spiderall (String subdomainof, String domainlike) {

if (!subdomainof.contains(".")||subdomainof.endsWith(".")||subdomainof.equals("")){
//如果域名为空,或者(不包含.号,或者点号在末尾的)
Expand All @@ -205,7 +213,7 @@ public Map spiderall (String subdomainof, String domainlike) {
int i = 0;
while(i<=2) {
IHttpRequestResponse[] items = callbacks.getSiteMap(null); //null to return entire sitemap
int len = items.length;
//int len = items.length;
//stdout.println("item number: "+len);

for (IHttpRequestResponse x:items){// 经过验证每次都需要从头开始遍历,按一定offset获取的数据每次都可能不同
Expand Down Expand Up @@ -377,8 +385,8 @@ protected Map doInBackground() throws Exception {
protected void done() {
try {
Map result = get();
subdomainofset = (Set) result.get("subdomainofset"); //之前的set变成了object
domainlikeset = (Set) result.get("domainlikeset");
subdomainofset = (Set<String>) result.get("subdomainofset"); //之前的set变成了object
domainlikeset = (Set<String>) result.get("domainlikeset");
textArea.setText(set2string(subdomainofset));
textArea_1.setText(set2string(domainlikeset));
btnNewButton.setEnabled(true);
Expand Down Expand Up @@ -502,4 +510,36 @@ public List<JMenuItem> createMenuItems(IContextMenuInvocation invocation) {

//IContextMenuFactory 必须实现的方法
//各种burp必须的方法 --end


public static boolean validIP (String ip) {
try {
if ( ip == null || ip.isEmpty() ) {
return false;
}

String[] parts = ip.split( "\\." );
if ( parts.length != 4 ) {
return false;
}

for ( String s : parts ) {
int i = Integer.parseInt( s );
if ( (i < 0) || (i > 255) ) {
return false;
}
}
if ( ip.endsWith(".") ) {
return false;
}

return true;
} catch (NumberFormatException nfe) {
return false;
}
}

public static void main(String args[]) {
System.out.println("aaa".contains(""));
}
}
3 changes: 1 addition & 2 deletions src/burp/CertInfo.java
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ public void checkClientTrusted(X509Certificate[] chain, String authType)
};


public static Set<String> getSANs(String aURL,String domain) throws Exception{//only when domain key word in the Principal,return SANs
public static Set<String> getSANs(String aURL,String domainKeyword) throws Exception{//only when domain key word in the Principal,return SANs
HostnameVerifier allHostsValid = new HostnameVerifier() {
public boolean verify(String hostname, SSLSession session) {
return true;
Expand Down Expand Up @@ -68,7 +68,6 @@ public boolean verify(String hostname, SSLSession session) {
//java.lang.NullPointerException. why??? need to confirm collection is not null

String Principal = cer.getSubjectX500Principal().getName();
String domainKeyword = domain.toLowerCase().split("\\.")[0];
if (Principal.toLowerCase().contains(domainKeyword)) {
//this may lead to miss some related domains, eg. https://www.YouTube.com ,it's principal is *.google.com
//but our target is to get useful message, so we need to do this to void CDN provider,I think it's worth~, or any good idea?
Expand Down
8 changes: 4 additions & 4 deletions src/burp/ThreadCertInfo.java
Original file line number Diff line number Diff line change
Expand Up @@ -41,16 +41,16 @@ public Set<String> call(){
*/

private String url;
private String domain;
public ThreadCertInfo(String url,String domain) {
private String domainKeyword;
public ThreadCertInfo(String url,String domainKeyword) {
this.url = url;
this.domain = domain;
this.domainKeyword = domainKeyword;
}


@Override
public Set<String> call() throws Exception{
Set<String> tmpDomains = CertInfo.getSANs(url,domain);
Set<String> tmpDomains = CertInfo.getSANs(url,domainKeyword);
return tmpDomains;
}

Expand Down

0 comments on commit 12022db

Please sign in to comment.