Version: 2.4.6 Update
This commit is contained in:
@@ -34,7 +34,7 @@ public class BurpExtender implements IBurpExtender, IHttpListener, IMessageEdito
|
|||||||
this.callbacks = callbacks;
|
this.callbacks = callbacks;
|
||||||
BurpExtender.helpers = callbacks.getHelpers();
|
BurpExtender.helpers = callbacks.getHelpers();
|
||||||
|
|
||||||
String version = "2.4.5";
|
String version = "2.4.6";
|
||||||
callbacks.setExtensionName(String.format("HaE (%s) - Highlighter and Extractor", version));
|
callbacks.setExtensionName(String.format("HaE (%s) - Highlighter and Extractor", version));
|
||||||
// 定义输出
|
// 定义输出
|
||||||
stdout = new PrintWriter(callbacks.getStdout(), true);
|
stdout = new PrintWriter(callbacks.getStdout(), true);
|
||||||
|
|||||||
@@ -1,5 +1,6 @@
|
|||||||
package burp.action;
|
package burp.action;
|
||||||
|
|
||||||
|
import burp.BurpExtender;
|
||||||
import java.nio.charset.StandardCharsets;
|
import java.nio.charset.StandardCharsets;
|
||||||
import java.util.*;
|
import java.util.*;
|
||||||
import burp.Config;
|
import burp.Config;
|
||||||
@@ -19,121 +20,127 @@ public class ExtractContent {
|
|||||||
public Map<String, Map<String, Object>> matchRegex(byte[] content, String headers, byte[] body, String scopeString, String host) {
|
public Map<String, Map<String, Object>> matchRegex(byte[] content, String headers, byte[] body, String scopeString, String host) {
|
||||||
Map<String, Map<String, Object>> map = new HashMap<>(); // 最终返回的结果
|
Map<String, Map<String, Object>> map = new HashMap<>(); // 最终返回的结果
|
||||||
Config.ruleConfig.keySet().forEach(i -> {
|
Config.ruleConfig.keySet().forEach(i -> {
|
||||||
String matchContent = "";
|
|
||||||
for (Object[] objects : Config.ruleConfig.get(i)) {
|
for (Object[] objects : Config.ruleConfig.get(i)) {
|
||||||
// 遍历获取规则
|
// 多线程执行,一定程度上减少阻塞现象
|
||||||
List<String> result = new ArrayList<>();
|
Thread t = new Thread(() -> {
|
||||||
Map<String, Object> tmpMap = new HashMap<>();
|
String matchContent = "";
|
||||||
|
// 遍历获取规则
|
||||||
|
List<String> result = new ArrayList<>();
|
||||||
|
Map<String, Object> tmpMap = new HashMap<>();
|
||||||
|
|
||||||
String name = objects[1].toString();
|
String name = objects[1].toString();
|
||||||
boolean loaded = (Boolean) objects[0];
|
boolean loaded = (Boolean) objects[0];
|
||||||
String regex = objects[2].toString();
|
String regex = objects[2].toString();
|
||||||
String color = objects[3].toString();
|
String color = objects[3].toString();
|
||||||
String scope = objects[4].toString();
|
String scope = objects[4].toString();
|
||||||
String engine = objects[5].toString();
|
String engine = objects[5].toString();
|
||||||
boolean sensitive = (Boolean) objects[6];
|
boolean sensitive = (Boolean) objects[6];
|
||||||
// 判断规则是否开启与作用域
|
// 判断规则是否开启与作用域
|
||||||
if (loaded && (scope.contains(scopeString) || scope.contains("any"))) {
|
if (loaded && (scope.contains(scopeString) || scope.contains("any"))) {
|
||||||
switch (scope) {
|
switch (scope) {
|
||||||
case "any":
|
case "any":
|
||||||
case "request":
|
case "request":
|
||||||
case "response":
|
case "response":
|
||||||
matchContent = new String(content, StandardCharsets.UTF_8).intern();
|
matchContent = new String(content, StandardCharsets.UTF_8).intern();
|
||||||
break;
|
break;
|
||||||
case "any header":
|
case "any header":
|
||||||
case "request header":
|
case "request header":
|
||||||
case "response header":
|
case "response header":
|
||||||
matchContent = headers;
|
matchContent = headers;
|
||||||
break;
|
break;
|
||||||
case "any body":
|
case "any body":
|
||||||
case "request body":
|
case "request body":
|
||||||
case "response body":
|
case "response body":
|
||||||
matchContent = new String(body, StandardCharsets.UTF_8).intern();
|
matchContent = new String(body, StandardCharsets.UTF_8).intern();
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
return;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ("nfa".equals(engine)) {
|
if ("nfa".equals(engine)) {
|
||||||
Pattern pattern;
|
Pattern pattern;
|
||||||
// 判断规则是否大小写敏感
|
// 判断规则是否大小写敏感
|
||||||
if (sensitive) {
|
if (sensitive) {
|
||||||
pattern = new Pattern(regex);
|
pattern = new Pattern(regex);
|
||||||
|
} else {
|
||||||
|
pattern = new Pattern(regex, Pattern.IGNORE_CASE);
|
||||||
|
}
|
||||||
|
|
||||||
|
Matcher matcher = pattern.matcher(matchContent);
|
||||||
|
while (matcher.find()) {
|
||||||
|
// 添加匹配数据至list
|
||||||
|
// 强制用户使用()包裹正则
|
||||||
|
result.add(matcher.group(1));
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
pattern = new Pattern(regex, Pattern.IGNORE_CASE);
|
RegExp regexp = new RegExp(regex);
|
||||||
|
Automaton auto = regexp.toAutomaton();
|
||||||
|
RunAutomaton runAuto = new RunAutomaton(auto, true);
|
||||||
|
AutomatonMatcher autoMatcher = runAuto.newMatcher(matchContent);
|
||||||
|
while (autoMatcher.find()) {
|
||||||
|
// 添加匹配数据至list
|
||||||
|
// 强制用户使用()包裹正则
|
||||||
|
result.add(autoMatcher.group());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Matcher matcher = pattern.matcher(matchContent);
|
// 去除重复内容
|
||||||
while (matcher.find()) {
|
HashSet tmpList = new HashSet(result);
|
||||||
// 添加匹配数据至list
|
result.clear();
|
||||||
// 强制用户使用()包裹正则
|
result.addAll(tmpList);
|
||||||
result.add(matcher.group(1));
|
|
||||||
}
|
if (!result.isEmpty()) {
|
||||||
} else {
|
tmpMap.put("color", color);
|
||||||
RegExp regexp = new RegExp(regex);
|
String dataStr = String.join("\n", result);
|
||||||
Automaton auto = regexp.toAutomaton();
|
tmpMap.put("data", dataStr);
|
||||||
RunAutomaton runAuto = new RunAutomaton(auto, true);
|
|
||||||
AutomatonMatcher autoMatcher = runAuto.newMatcher(matchContent);
|
// 添加到全局变量中,便于Databoard检索
|
||||||
while (autoMatcher.find()) {
|
if (!host.isEmpty()) {
|
||||||
// 添加匹配数据至list
|
String anyHost = host.replace(host.split("\\.")[0], "*");
|
||||||
// 强制用户使用()包裹正则
|
List<String> dataList = Arrays.asList(dataStr.split("\n"));
|
||||||
result.add(autoMatcher.group());
|
if (Config.globalDataMap.containsKey(host)) {
|
||||||
|
Map<String, List<String>> gRuleMap = Config.globalDataMap.get(host);
|
||||||
|
// 判断匹配规则是否存在(逻辑同Host判断)
|
||||||
|
if (gRuleMap.containsKey(name)) {
|
||||||
|
List<String> gDataList = gRuleMap.get(name);
|
||||||
|
List<String> mergeDataList = new ArrayList<>(gDataList);
|
||||||
|
// 合并两个List
|
||||||
|
mergeDataList.addAll(dataList);
|
||||||
|
// 去重操作
|
||||||
|
tmpList = new HashSet(mergeDataList);
|
||||||
|
mergeDataList.clear();
|
||||||
|
mergeDataList.addAll(tmpList);
|
||||||
|
// 替换操作
|
||||||
|
gRuleMap.replace(name, gDataList, mergeDataList);
|
||||||
|
} else {
|
||||||
|
gRuleMap.put(name, dataList);
|
||||||
|
}
|
||||||
|
} else if (!Config.globalDataMap.containsKey(anyHost)) {
|
||||||
|
// 添加通配符Host
|
||||||
|
Config.globalDataMap.put(anyHost, new HashMap<>());
|
||||||
|
} else {
|
||||||
|
Map<String, List<String>> ruleMap = new HashMap<>();
|
||||||
|
ruleMap.put(name, dataList);
|
||||||
|
// 添加单一Host
|
||||||
|
Config.globalDataMap.put(host, ruleMap);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
map.put(name, tmpMap);
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
});
|
||||||
// 去除重复内容
|
t.start();
|
||||||
HashSet tmpList = new HashSet(result);
|
try {
|
||||||
result.clear();
|
t.join();
|
||||||
result.addAll(tmpList);
|
} catch (InterruptedException e) {
|
||||||
|
e.printStackTrace();
|
||||||
if (!result.isEmpty()) {
|
|
||||||
tmpMap.put("color", color);
|
|
||||||
tmpMap.put("data", String.join("\n", result));
|
|
||||||
// 初始化格式
|
|
||||||
map.put(name, tmpMap);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
// 将提取的数据存放到全局变量中
|
|
||||||
if (!host.isEmpty()) {
|
|
||||||
map.keySet().forEach(i -> {
|
|
||||||
Map<String, Object> tmpMap = map.get(i);
|
|
||||||
List<String> dataList = Arrays.asList(tmpMap.get("data").toString().split("\n"));
|
|
||||||
// 组合通配符Host
|
|
||||||
String anyHost = host.replace(host.split("\\.")[0], "*");
|
|
||||||
// 判断Host是否存在,如存在则进行数据更新,反之则新增数据
|
|
||||||
if (Config.globalDataMap.containsKey(host)) {
|
|
||||||
Map<String, List<String>> gRuleMap = Config.globalDataMap.get(host);
|
|
||||||
// 判断匹配规则是否存在(逻辑同Host判断)
|
|
||||||
if (gRuleMap.containsKey(i)) {
|
|
||||||
List<String> gDataList = gRuleMap.get(i);
|
|
||||||
List<String> mergeDataList = new ArrayList<>(gDataList);
|
|
||||||
// 合并两个List
|
|
||||||
mergeDataList.addAll(dataList);
|
|
||||||
// 去重操作
|
|
||||||
HashSet tmpList = new HashSet(mergeDataList);
|
|
||||||
mergeDataList.clear();
|
|
||||||
mergeDataList.addAll(tmpList);
|
|
||||||
// 替换操作
|
|
||||||
gRuleMap.replace(i, gDataList, mergeDataList);
|
|
||||||
} else {
|
|
||||||
gRuleMap.put(i, dataList);
|
|
||||||
}
|
|
||||||
} else if (!Config.globalDataMap.containsKey(anyHost)) {
|
|
||||||
// 添加通配符Host
|
|
||||||
Config.globalDataMap.put(anyHost, new HashMap<>());
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
Map<String, List<String>> ruleMap = new HashMap<>();
|
|
||||||
ruleMap.put(i, dataList);
|
|
||||||
// 添加单一Host
|
|
||||||
Config.globalDataMap.put(host, ruleMap);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
return map;
|
return map;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user