com.codemagi.burp.RuleTableComponent Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of burp-suite-utils Show documentation
Show all versions of burp-suite-utils Show documentation
The Burp Suite Utils project provides developers with APIs for building Burp Suite Extensions.
package com.codemagi.burp;
import burp.IBurpExtenderCallbacks;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.io.PrintStream;
import java.net.URL;
import java.util.regex.Pattern;
import javax.swing.DefaultCellEditor;
import javax.swing.event.TableModelEvent;
import javax.swing.event.TableModelListener;
import javax.swing.table.DefaultTableModel;
import javax.swing.table.TableColumn;
public class RuleTableComponent extends javax.swing.JPanel {
IBurpExtenderCallbacks mCallbacks;
PassiveScan scan;
private String DEFAULT_URL = "https://raw.githubusercontent.com/augustd/burp-suite-software-version-checks/master/src/burp/match-rules.tab";
public static final String SETTING_URL = "SETTING_URL";
/**
* Creates new form BurpSuiteTab
*
* @param passiveScan The scan to initialize this component for
* @param callbacks The Burp Extender callbacks object
* @param defaultUrl The default URL to load match rules from
*/
public RuleTableComponent(PassiveScan passiveScan, IBurpExtenderCallbacks callbacks, String defaultUrl) {
mCallbacks = callbacks;
this.scan = passiveScan;
this.DEFAULT_URL = defaultUrl;
initComponents();
mCallbacks.customizeUiComponent(rules);
//restore saved settings
restoreSettings();
//load match rules from GitHub
loadMatchRules(urlTextField.getText());
//add a listener for changes to the table model
final DefaultTableModel model = (DefaultTableModel)rules.getModel();
model.addTableModelListener(new TableModelListener() {
@Override
public void tableChanged(TableModelEvent e) {
if (TableModelEvent.UPDATE == e.getType()) {
mCallbacks.printOutput(e.toString());
int row = e.getFirstRow();
int column = e.getColumn();
mCallbacks.printOutput("row: " + row + " column: " + column + " value: " + model.getValueAt(row, column));
MatchRule rule = scan.getMatchRule(row);
mCallbacks.printOutput("rule 1: " + rule);
if (rule == null) {
rule = new MatchRule(Pattern.compile("."), 1, "", ScanIssueSeverity.LOW, ScanIssueConfidence.CERTAIN);
scan.addMatchRule(rule);
}
mCallbacks.printOutput("rule 2: " + rule);
switch (column) {
case 0:
mCallbacks.printOutput("new pattern: " + (String)model.getValueAt(row, column));
rule.setPattern(Pattern.compile((String)model.getValueAt(row, column)));
break;
case 1:
rule.setMatchGroup((Integer)model.getValueAt(row, column));
break;
case 2:
rule.setType((String)model.getValueAt(row, column));
break;
case 3:
rule.setSeverity(ScanIssueSeverity.fromName((String)model.getValueAt(row, column)));
break;
case 4:
rule.setConfidence(ScanIssueConfidence.fromName((String)model.getValueAt(row, column)));
break;
}
}
}
});
}
/**
* Load match rules from a file
*/
private boolean loadMatchRules(String url) {
//load match rules from file
try {
DefaultTableModel model = (DefaultTableModel)rules.getModel();
//read match rules from the stream
InputStream is = new URL(url).openStream();
BufferedReader reader = new BufferedReader(new InputStreamReader(is, "UTF-8"));
String str;
while ((str = reader.readLine()) != null) {
mCallbacks.printOutput("str: " + str);
if (str.trim().length() == 0) {
continue;
}
String[] values = str.split("\\t");
model.addRow(values);
Pattern pattern = Pattern.compile(values[0]);
scan.addMatchRule(new MatchRule(
pattern,
new Integer(values[1]),
values[2],
ScanIssueSeverity.fromName(values[3]),
ScanIssueConfidence.fromName(values[4]))
);
}
return true;
} catch (IOException e) {
OutputStream error = mCallbacks.getStderr();
e.printStackTrace(new PrintStream(error));
} catch (NumberFormatException e) {
OutputStream error = mCallbacks.getStderr();
e.printStackTrace(new PrintStream(error));
}
return false;
}
/**
* Save all configured settings
*/
public void saveSettings() {
mCallbacks.printOutput("Saving settings...");
// Clear settings
mCallbacks.saveExtensionSetting(scan.getSettingsNamespace() + SETTING_URL, null);
// Store settings
mCallbacks.printOutput("Saving URL: " + urlTextField.getText());
mCallbacks.saveExtensionSetting(scan.getSettingsNamespace() + SETTING_URL, urlTextField.getText());
}
/**
* Restores any found saved settings
*/
public void restoreSettings() {
mCallbacks.printOutput("Restoring settings...");
String settingUrl = mCallbacks.loadExtensionSetting(scan.getSettingsNamespace() + SETTING_URL);
mCallbacks.printOutput("Loaded URL: " + settingUrl);
if (settingUrl != null) {
urlTextField.setText(settingUrl);
//extender.setFormUrl(settingUrl);
}
}
/**
* This method is called from within the constructor to initialize the form. WARNING: Do NOT modify this code. The content of this method is always regenerated by the Form Editor.
*/
@SuppressWarnings("unchecked")
// //GEN-BEGIN:initComponents
private void initComponents() {
jScrollPane2 = new javax.swing.JScrollPane();
rules = new javax.swing.JTable();
jLabel2 = new javax.swing.JLabel();
jLabel6 = new javax.swing.JLabel();
urlTextField = new javax.swing.JTextField();
loadBtn = new javax.swing.JButton();
jLabel7 = new javax.swing.JLabel();
addBtn = new javax.swing.JButton();
removeBtn = new javax.swing.JButton();
resetButton = new javax.swing.JButton();
rules.setModel(new javax.swing.table.DefaultTableModel(
new Object [][] {
},
new String [] {
"Regex", "Group", "Type", "Severity", "Confidence"
}
) {
Class[] types = new Class [] {
java.lang.String.class, java.lang.Integer.class, java.lang.String.class, java.lang.String.class, java.lang.String.class
};
public Class getColumnClass(int columnIndex) {
return types [columnIndex];
}
});
TableColumn severityColumn = rules.getColumnModel().getColumn(3);
severityColumn.setCellEditor(new DefaultCellEditor(ScanIssueSeverity.getComboBox()));
TableColumn confidenceColumn = rules.getColumnModel().getColumn(4);
confidenceColumn.setCellEditor(new DefaultCellEditor(ScanIssueConfidence.getComboBox()));
jScrollPane2.setViewportView(rules);
jLabel2.setFont(new java.awt.Font("Tahoma", 1, 13)); // NOI18N
jLabel2.setForeground(new java.awt.Color(229, 137, 0));
jLabel2.setText("Match Rules");
jLabel6.setText("Match rules use regular epressions to flag software version numbers in server responses");
urlTextField.setText(DEFAULT_URL);
urlTextField.addActionListener(new java.awt.event.ActionListener() {
public void actionPerformed(java.awt.event.ActionEvent evt) {
urlTextFieldActionPerformed(evt);
}
});
loadBtn.setText("Load");
loadBtn.setIgnoreRepaint(true);
loadBtn.addActionListener(new java.awt.event.ActionListener() {
public void actionPerformed(java.awt.event.ActionEvent evt) {
loadBtnActionPerformed(evt);
}
});
jLabel7.setText("Load rules from URL: ");
addBtn.setText("Add");
addBtn.addActionListener(new java.awt.event.ActionListener() {
public void actionPerformed(java.awt.event.ActionEvent evt) {
addBtnActionPerformed(evt);
}
});
removeBtn.setText("Remove");
removeBtn.addActionListener(new java.awt.event.ActionListener() {
public void actionPerformed(java.awt.event.ActionEvent evt) {
removeBtnActionPerformed(evt);
}
});
resetButton.setText("Reset");
resetButton.setToolTipText("Reload default match rules from GitHub");
resetButton.addActionListener(new java.awt.event.ActionListener() {
public void actionPerformed(java.awt.event.ActionEvent evt) {
resetButtonActionPerformed(evt);
}
});
javax.swing.GroupLayout layout = new javax.swing.GroupLayout(this);
this.setLayout(layout);
layout.setHorizontalGroup(
layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(layout.createSequentialGroup()
.addContainerGap()
.addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addComponent(jScrollPane2)
.addGroup(layout.createSequentialGroup()
.addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addComponent(jLabel2)
.addComponent(jLabel6)
.addGroup(layout.createSequentialGroup()
.addComponent(addBtn)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
.addComponent(removeBtn)))
.addGap(0, 0, Short.MAX_VALUE))
.addGroup(layout.createSequentialGroup()
.addComponent(jLabel7)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
.addComponent(urlTextField, javax.swing.GroupLayout.PREFERRED_SIZE, 406, javax.swing.GroupLayout.PREFERRED_SIZE)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addComponent(loadBtn)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
.addComponent(resetButton)))
.addContainerGap())
);
layout.setVerticalGroup(
layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(layout.createSequentialGroup()
.addContainerGap()
.addComponent(jLabel2, javax.swing.GroupLayout.PREFERRED_SIZE, 16, javax.swing.GroupLayout.PREFERRED_SIZE)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
.addComponent(jLabel6)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
.addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
.addComponent(urlTextField, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
.addComponent(jLabel7)
.addComponent(loadBtn)
.addComponent(resetButton))
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
.addComponent(jScrollPane2, javax.swing.GroupLayout.PREFERRED_SIZE, 381, javax.swing.GroupLayout.PREFERRED_SIZE)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
.addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
.addComponent(addBtn)
.addComponent(removeBtn))
.addContainerGap(12, Short.MAX_VALUE))
);
}// //GEN-END:initComponents
private void loadBtnActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_loadBtnActionPerformed
//read value from text field
String url = urlTextField.getText();
//issue request to URL
boolean success = loadMatchRules(url);
if (success) saveSettings();
}//GEN-LAST:event_loadBtnActionPerformed
private void urlTextFieldActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_urlTextFieldActionPerformed
// TODO add your handling code here:
}//GEN-LAST:event_urlTextFieldActionPerformed
private void addBtnActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_addBtnActionPerformed
DefaultTableModel model = (DefaultTableModel)rules.getModel();
model.addRow(new Object[]{"", 1, "", "Low", "Certain"});
}//GEN-LAST:event_addBtnActionPerformed
private void removeBtnActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_removeBtnActionPerformed
DefaultTableModel model = (DefaultTableModel)rules.getModel();
int[] rows = rules.getSelectedRows();
for (int i = 0; i < rows.length; i++) {
model.removeRow(rows[i] - i);
scan.removeMatchRule(rows[i] - i);
}
}//GEN-LAST:event_removeBtnActionPerformed
private void resetButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_resetButtonActionPerformed
//clear the existing values from the table
DefaultTableModel model = (DefaultTableModel) rules.getModel();
model.setRowCount(0);
//remove existing match rules from the scan
scan.clearMatchRules();
//load the defaults
urlTextField.setText(DEFAULT_URL);
loadMatchRules(DEFAULT_URL);
saveSettings();
}//GEN-LAST:event_resetButtonActionPerformed
// Variables declaration - do not modify//GEN-BEGIN:variables
private javax.swing.JButton addBtn;
private javax.swing.JLabel jLabel2;
private javax.swing.JLabel jLabel6;
private javax.swing.JLabel jLabel7;
private javax.swing.JScrollPane jScrollPane2;
private javax.swing.JButton loadBtn;
private javax.swing.JButton removeBtn;
private javax.swing.JButton resetButton;
private javax.swing.JTable rules;
private javax.swing.JTextField urlTextField;
// End of variables declaration//GEN-END:variables
}
© 2015 - 2024 Weber Informatics LLC | Privacy Policy