├── .gitignore
├── README.md
├── figures
├── tls-attacks.png
├── tls-recommendations.png
├── tls-scoring.png
└── tls-versions.png
├── license_header.txt
├── pom.xml
└── src
└── main
├── java
├── burp
│ └── BurpExtender.java
└── de
│ └── rub
│ └── nds
│ └── burp
│ ├── tlsattacker
│ └── gui
│ │ ├── UIMain.java
│ │ ├── UIScanHistory.form
│ │ ├── UIScanHistory.java
│ │ ├── UIScanner.form
│ │ ├── UIScanner.java
│ │ └── UITab.java
│ └── utilities
│ ├── ANSIHelper.java
│ └── table
│ ├── TableEntry.java
│ └── TableModel.java
└── resources
└── de.rub.nds.burp.tlsattacker.log4j2.xml
/.gitignore:
--------------------------------------------------------------------------------
1 | dependency-reduced-pom.xml
2 | *.log
3 | nbactions.xml
4 | nb-configuration.xml
5 | pom.xml.next
6 | pom.xml.releaseBackup
7 | pom.xml.tag
8 | pom.xml.versionsBackup
9 | release.properties
10 | *.swo
11 | *.swp
12 | target/
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # TLS-Attacker-BurpExtension
2 |
3 | The extension is based on the [TLS-Attacker](https://github.com/RUB-NDS/TLS-Attacker) and developed by the [Chair for Network and Data Security from the Ruhr-University Bochum](http://nds.rub.de/) to assist pentesters and security researchers in the evaluation of TLS Server configurations with [Burp Suite](https://portswigger.net/burp).
4 |
5 | ## Build
6 | To compile the extension from source, you need to have Java and Maven installed, as well as [TLS-Attacker](https://github.com/RUB-NDS/TLS-Attacker) in Version 3.3.1 and [TLS-Scanner](https://github.com/RUB-NDS/TLS-Scanner) in Version 3.0.2.
7 | ```bash
8 | $ mvn clean package
9 | ```
10 | The extension has been tested with Java 1.8.
11 |
12 | ## Installation
13 | - Build the JAR file as described above, or download it from [releases](https://github.com/RUB-NDS/TLS-Attacker-BurpExtension/releases).
14 | - Load the JAR file from the target folder into Burp's Extender.
15 |
16 | ## Usage
17 | Use the URL and port of the tested server and start the scan.
18 | The scan can last up to one minute, depending on the availability of the server.
19 | After the scan has been finished, you will find the following scanning output, for example:
20 |
21 | **Supported versions and cipher suites:**
22 |
23 | 
24 |
25 | **Analyzed attacks and vulnerabilities:**
26 |
27 | 
28 |
29 | **Resulting score based on the analyzed properties:**
30 |
31 | 
32 |
33 | **Recommendations to improve your implementation configuration:**
34 |
35 | 
36 |
--------------------------------------------------------------------------------
/figures/tls-attacks.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/tls-attacker/TLS-Attacker-BurpExtension/22c0dea77a6697af555f4e529e046b9f51441bc6/figures/tls-attacks.png
--------------------------------------------------------------------------------
/figures/tls-recommendations.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/tls-attacker/TLS-Attacker-BurpExtension/22c0dea77a6697af555f4e529e046b9f51441bc6/figures/tls-recommendations.png
--------------------------------------------------------------------------------
/figures/tls-scoring.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/tls-attacker/TLS-Attacker-BurpExtension/22c0dea77a6697af555f4e529e046b9f51441bc6/figures/tls-scoring.png
--------------------------------------------------------------------------------
/figures/tls-versions.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/tls-attacker/TLS-Attacker-BurpExtension/22c0dea77a6697af555f4e529e046b9f51441bc6/figures/tls-versions.png
--------------------------------------------------------------------------------
/license_header.txt:
--------------------------------------------------------------------------------
1 | TLS-Attacker-BurpExtension
2 |
3 | Copyright 2018 Ruhr University Bochum / Hackmanit GmbH
4 |
5 | Licensed under Apache License 2.0
6 | http://www.apache.org/licenses/LICENSE-2.0/
--------------------------------------------------------------------------------
/pom.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 | 4.0.0
4 | de.rub.nds.tlsattacker
5 | TLS-Attacker-BurpExtension
6 | 1.2
7 | jar
8 | 2018
9 |
10 |
11 |
12 | net.portswigger.burp.extender
13 | burp-extender-api
14 | 1.7.22
15 |
16 |
17 |
18 | de.rub.nds.tlsscanner
19 | TLS-Scanner
20 | 3.0.2
21 |
22 |
23 |
24 | UTF-8
25 | 1.8
26 | 1.8
27 |
28 |
29 |
30 |
31 |
32 | com.mycila
33 | license-maven-plugin
34 | 2.11
35 |
36 | ${basedir}/license_header.txt
37 | true
38 |
39 | src/**/*.java
40 |
41 |
42 |
43 |
44 |
45 | check
46 |
47 |
48 |
49 |
50 |
51 |
52 | maven-compiler-plugin
53 | 3.7.0
54 |
55 | 1.8
56 | 1.8
57 |
58 |
59 |
60 |
61 | maven-assembly-plugin
62 | 2.6
63 |
64 |
65 | jar-with-dependencies
66 |
67 |
68 |
69 |
70 | make-assembly
71 | package
72 |
73 | single
74 |
75 |
76 |
77 |
78 |
79 |
80 |
81 |
--------------------------------------------------------------------------------
/src/main/java/burp/BurpExtender.java:
--------------------------------------------------------------------------------
1 | /**
2 | * TLS-Attacker-BurpExtension
3 | *
4 | * Copyright 2018 Ruhr University Bochum / Hackmanit GmbH
5 | *
6 | * Licensed under Apache License 2.0
7 | * http://www.apache.org/licenses/LICENSE-2.0/
8 | */
9 | package burp;
10 |
11 | import de.rub.nds.burp.tlsattacker.gui.UITab;
12 | import org.apache.logging.log4j.Level;
13 | import org.apache.logging.log4j.LogManager;
14 | import org.apache.logging.log4j.core.Filter;
15 | import org.apache.logging.log4j.core.LoggerContext;
16 | import org.apache.logging.log4j.core.appender.WriterAppender;
17 | import org.apache.logging.log4j.core.config.Configuration;
18 | import org.apache.logging.log4j.core.config.LoggerConfig;
19 | import org.apache.logging.log4j.core.filter.ThresholdFilter;
20 | import org.apache.logging.log4j.core.layout.PatternLayout;
21 | import java.io.PrintWriter;
22 | import java.time.LocalTime;
23 | import org.apache.logging.log4j.Logger;
24 |
25 | /**
26 | * The first class called by Burp Suite.
27 | * This is the starting class for all other functionalities.
28 | *
29 | * @author Nurullah Erinola
30 | */
31 | public class BurpExtender implements IBurpExtender {
32 |
33 | private static final Logger LOGGER = LogManager.getLogger(BurpExtender.class.getName());
34 | public static final String EXTENSION_NAME = "TLS-Attacker";
35 |
36 | private UITab tab;
37 | private static PrintWriter stdout;
38 | private static PrintWriter stderr;
39 |
40 | /**
41 | * Register all new functions like for the internals and GUI.
42 | */
43 | @Override
44 | public void registerExtenderCallbacks(IBurpExtenderCallbacks callbacks) {
45 | // Set extension name
46 | callbacks.setExtensionName(EXTENSION_NAME);
47 | // Oprain streans
48 | stdout = new PrintWriter(callbacks.getStdout(), true);
49 | stderr = new PrintWriter(callbacks.getStderr(), true);
50 |
51 | LocalTime t = LocalTime.now();
52 | String time = t.toString().substring(0, t.toString().length()-4);
53 | stdout.println("+------------------------------+");
54 | stdout.println("| TLS-Attacker |");
55 | stdout.println("| Started @ "+time+" |");
56 | stdout.println("+------------------------------+");
57 |
58 | // Setup Logger
59 | System.setProperty("log4j.configurationFile", "de.rub.nds.burp.tlsattacker.log4j2.xml");
60 | addBurpLogger();
61 |
62 | // Register a new Tab
63 | tab = new UITab(callbacks);
64 | LOGGER.info("Tab registered.");
65 |
66 | // Register a new context menu item
67 | callbacks.registerContextMenuFactory(tab.getUiComponent().getScanner());
68 |
69 | LOGGER.info("Init. complete.");
70 | }
71 |
72 | private void addBurpLogger() {
73 | // currentContext must be set to false
74 | final LoggerContext ctx = (LoggerContext) LogManager.getContext(false);
75 | final Configuration config = ctx.getConfiguration();
76 |
77 | // use empty string to get config of root logger, LogManager.ROOT_LOGGER_NAME did not work for unknown reasons
78 | LoggerConfig rootLoggerCfg = config.getLoggerConfig(LogManager.ROOT_LOGGER_NAME);
79 |
80 | PatternLayout layout = PatternLayout.newBuilder().withPattern("%d{HH:mm:ss}{GMT+0} [%t] %-5level: %c{1} - %msg%n%throwable").build();
81 |
82 | // create appender to log <= INFO to burp's stdout writer
83 | Filter infoFilter = ThresholdFilter.createFilter(Level.WARN, Filter.Result.DENY, Filter.Result.ACCEPT);
84 | WriterAppender stdoutAppender = WriterAppender.newBuilder().setName("stdoutLogger").setTarget(stdout)
85 | .setLayout(layout).setFilter(infoFilter).build();
86 | stdoutAppender.start();
87 |
88 | // create appender to log >= INFO to burp's sterr writer
89 | Filter warnFilter = ThresholdFilter.createFilter(Level.WARN, Filter.Result.ACCEPT, Filter.Result.DENY);
90 | WriterAppender stderrAppender = WriterAppender.newBuilder().setName("stderrLogger").setTarget(stderr)
91 | .setLayout(layout).setFilter(warnFilter).build();
92 | stderrAppender.start();
93 |
94 | rootLoggerCfg.addAppender(stdoutAppender, null, null);
95 | rootLoggerCfg.addAppender(stderrAppender, null, null);
96 |
97 | ctx.updateLoggers();
98 | }
99 | }
100 |
--------------------------------------------------------------------------------
/src/main/java/de/rub/nds/burp/tlsattacker/gui/UIMain.java:
--------------------------------------------------------------------------------
1 | /**
2 | * TLS-Attacker-BurpExtension
3 | *
4 | * Copyright 2018 Ruhr University Bochum / Hackmanit GmbH
5 | *
6 | * Licensed under Apache License 2.0
7 | * http://www.apache.org/licenses/LICENSE-2.0/
8 | */
9 | package de.rub.nds.burp.tlsattacker.gui;
10 |
11 | import burp.IBurpExtenderCallbacks;
12 | import javax.swing.JTabbedPane;
13 |
14 | /**
15 | * The main window.
16 | *
17 | * @author Nurullah Erinola
18 | */
19 | public class UIMain extends JTabbedPane {
20 |
21 | private final IBurpExtenderCallbacks callbacks;
22 | private UIScanner scanner;
23 | private UIScanHistory scanHistory;
24 |
25 | /**
26 | * Construct the main UI.
27 | * @param callbacks
28 | */
29 | public UIMain(IBurpExtenderCallbacks callbacks) {
30 | this.callbacks = callbacks;
31 | initComponents();
32 | }
33 |
34 | private void initComponents() {
35 | //register all components on the extension tab
36 | scanHistory = new UIScanHistory();
37 | scanner = new UIScanner(scanHistory);
38 | this.addTab("TLS-Scanner", scanner);
39 | this.addTab("Scan History", scanHistory);
40 |
41 | // Customize the UI components
42 | callbacks.customizeUiComponent(this);
43 | }
44 |
45 | public UIScanner getScanner(){
46 | return scanner;
47 | }
48 | }
49 |
--------------------------------------------------------------------------------
/src/main/java/de/rub/nds/burp/tlsattacker/gui/UIScanHistory.form:
--------------------------------------------------------------------------------
1 |
2 |
3 |
118 |
--------------------------------------------------------------------------------
/src/main/java/de/rub/nds/burp/tlsattacker/gui/UIScanHistory.java:
--------------------------------------------------------------------------------
1 | /**
2 | * TLS-Attacker-BurpExtension
3 | *
4 | * Copyright 2018 Ruhr University Bochum / Hackmanit GmbH
5 | *
6 | * Licensed under Apache License 2.0
7 | * http://www.apache.org/licenses/LICENSE-2.0/
8 | */
9 | package de.rub.nds.burp.tlsattacker.gui;
10 |
11 | import de.rub.nds.burp.utilities.ANSIHelper;
12 | import de.rub.nds.burp.utilities.table.TableEntry;
13 | import de.rub.nds.burp.utilities.table.TableModel;
14 | import de.rub.nds.tlsscanner.config.ScannerConfig;
15 | import de.rub.nds.tlsscanner.report.SiteReport;
16 | import java.awt.Toolkit;
17 | import java.awt.datatransfer.Clipboard;
18 | import java.awt.datatransfer.StringSelection;
19 | import javax.swing.JTable;
20 | import javax.swing.ListSelectionModel;
21 | import javax.swing.event.ListSelectionEvent;
22 | import javax.swing.event.ListSelectionListener;
23 | import javax.swing.table.TableRowSorter;
24 |
25 | /**
26 | * Scan History displays all scanned Hosts and their reports.
27 | *
28 | * @author Nurullah Erinola
29 | */
30 | public class UIScanHistory extends javax.swing.JPanel {
31 |
32 | private TableModel tableModel;
33 | private JTable table;
34 |
35 | /**
36 | * Creates new form UIScanHistory
37 | */
38 | public UIScanHistory() {
39 | initComponents();
40 | initTable();
41 | }
42 |
43 | /**
44 | * This method is called from within the constructor to initialize the form.
45 | * WARNING: Do NOT modify this code. The content of this method is always
46 | * regenerated by the Form Editor.
47 | */
48 | @SuppressWarnings("unchecked")
49 | // //GEN-BEGIN:initComponents
50 | private void initComponents() {
51 |
52 | jLabel1 = new javax.swing.JLabel();
53 | jLabel2 = new javax.swing.JLabel();
54 | jScrollPane2 = new javax.swing.JScrollPane();
55 | jTextPaneResult = new javax.swing.JTextPane();
56 | jButtonCopy = new javax.swing.JButton();
57 | jScrollPaneTable = new javax.swing.JScrollPane();
58 | jButtonClear = new javax.swing.JButton();
59 |
60 | jLabel1.setText("Select Host:");
61 |
62 | jLabel2.setText("Report:");
63 |
64 | jTextPaneResult.setEditable(false);
65 | jTextPaneResult.setFont(new java.awt.Font("Monospaced", 0, 14)); // NOI18N
66 | jScrollPane2.setViewportView(jTextPaneResult);
67 |
68 | jButtonCopy.setText("Copy");
69 | jButtonCopy.setToolTipText("Copy report to clipboard.");
70 | jButtonCopy.addActionListener(new java.awt.event.ActionListener() {
71 | public void actionPerformed(java.awt.event.ActionEvent evt) {
72 | jButtonCopyActionPerformed(evt);
73 | }
74 | });
75 |
76 | jButtonClear.setText("Clear");
77 | jButtonClear.setToolTipText("Remove all entries from history.");
78 | jButtonClear.addActionListener(new java.awt.event.ActionListener() {
79 | public void actionPerformed(java.awt.event.ActionEvent evt) {
80 | jButtonClearActionPerformed(evt);
81 | }
82 | });
83 |
84 | javax.swing.GroupLayout layout = new javax.swing.GroupLayout(this);
85 | this.setLayout(layout);
86 | layout.setHorizontalGroup(
87 | layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
88 | .addGroup(layout.createSequentialGroup()
89 | .addContainerGap()
90 | .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
91 | .addComponent(jScrollPane2, javax.swing.GroupLayout.Alignment.TRAILING)
92 | .addComponent(jScrollPaneTable)
93 | .addGroup(layout.createSequentialGroup()
94 | .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
95 | .addGroup(layout.createSequentialGroup()
96 | .addComponent(jLabel2)
97 | .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
98 | .addComponent(jButtonCopy))
99 | .addGroup(layout.createSequentialGroup()
100 | .addComponent(jLabel1)
101 | .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
102 | .addComponent(jButtonClear)))
103 | .addGap(0, 372, Short.MAX_VALUE)))
104 | .addContainerGap())
105 | );
106 | layout.setVerticalGroup(
107 | layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
108 | .addGroup(layout.createSequentialGroup()
109 | .addContainerGap()
110 | .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
111 | .addComponent(jLabel1)
112 | .addComponent(jButtonClear))
113 | .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
114 | .addComponent(jScrollPaneTable, javax.swing.GroupLayout.PREFERRED_SIZE, 111, javax.swing.GroupLayout.PREFERRED_SIZE)
115 | .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
116 | .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
117 | .addComponent(jLabel2)
118 | .addComponent(jButtonCopy))
119 | .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
120 | .addComponent(jScrollPane2, javax.swing.GroupLayout.DEFAULT_SIZE, 184, Short.MAX_VALUE)
121 | .addContainerGap())
122 | );
123 | }// //GEN-END:initComponents
124 |
125 | private void initTable() {
126 | tableModel = new TableModel();
127 | table = new JTable(tableModel);
128 | table.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
129 | table.getSelectionModel().addListSelectionListener(new ListSelectionListener() {
130 | @Override
131 | public void valueChanged(ListSelectionEvent lse) {
132 | SiteReport report = tableModel.getTableList().get(table.getSelectedRow()).getSiteReport();
133 | ScannerConfig config = tableModel.getTableList().get(table.getSelectedRow()).getConfig();
134 | String fullReport = report.getFullReport(config.getReportDetail(), !config.isNoColor());
135 | jTextPaneResult.setStyledDocument(ANSIHelper.getStyledDocument(fullReport));
136 | jTextPaneResult.setCaretPosition(0);
137 | }
138 | });
139 | jScrollPaneTable.setViewportView(table);
140 |
141 | //Enable sorting
142 | TableRowSorter sorter = new TableRowSorter<>();
143 | table.setRowSorter(sorter);
144 | sorter.setModel(tableModel);
145 | }
146 |
147 | public void add(ScannerConfig config, SiteReport report) {
148 | tableModel.addRow(new TableEntry(tableModel.getRowCount(), report, config));
149 | }
150 |
151 | private void jButtonCopyActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_jButtonCopyActionPerformed
152 | String toCopy = jTextPaneResult.getText();
153 | StringSelection stringSelection = new StringSelection(toCopy);
154 | Clipboard clpbrd = Toolkit.getDefaultToolkit().getSystemClipboard();
155 | clpbrd.setContents(stringSelection, null);
156 | }//GEN-LAST:event_jButtonCopyActionPerformed
157 |
158 | private void jButtonClearActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_jButtonClearActionPerformed
159 | tableModel.clear();
160 | jTextPaneResult.setText("");
161 | }//GEN-LAST:event_jButtonClearActionPerformed
162 |
163 | // Variables declaration - do not modify//GEN-BEGIN:variables
164 | private javax.swing.JButton jButtonClear;
165 | private javax.swing.JButton jButtonCopy;
166 | private javax.swing.JLabel jLabel1;
167 | private javax.swing.JLabel jLabel2;
168 | private javax.swing.JScrollPane jScrollPane2;
169 | private javax.swing.JScrollPane jScrollPaneTable;
170 | private javax.swing.JTextPane jTextPaneResult;
171 | // End of variables declaration//GEN-END:variables
172 | }
173 |
--------------------------------------------------------------------------------
/src/main/java/de/rub/nds/burp/tlsattacker/gui/UIScanner.form:
--------------------------------------------------------------------------------
1 |
2 |
3 |
310 |
--------------------------------------------------------------------------------
/src/main/java/de/rub/nds/burp/tlsattacker/gui/UIScanner.java:
--------------------------------------------------------------------------------
1 | /**
2 | * TLS-Attacker-BurpExtension
3 | *
4 | * Copyright 2018 Ruhr University Bochum / Hackmanit GmbH
5 | *
6 | * Licensed under Apache License 2.0
7 | * http://www.apache.org/licenses/LICENSE-2.0/
8 | */
9 | package de.rub.nds.burp.tlsattacker.gui;
10 |
11 | import burp.IContextMenuFactory;
12 | import burp.IContextMenuInvocation;
13 | import de.rub.nds.burp.utilities.ANSIHelper;
14 | import de.rub.nds.tlsattacker.core.config.delegate.GeneralDelegate;
15 | import de.rub.nds.tlsattacker.core.constants.StarttlsType;
16 | import de.rub.nds.tlsscanner.TlsScanner;
17 | import de.rub.nds.tlsscanner.config.ScannerConfig;
18 | import de.rub.nds.tlsscanner.constants.ScannerDetail;
19 | import de.rub.nds.tlsscanner.report.SiteReport;
20 | import java.awt.Toolkit;
21 | import java.awt.datatransfer.Clipboard;
22 | import java.awt.datatransfer.StringSelection;
23 | import java.awt.event.ActionListener;
24 | import java.util.ArrayList;
25 | import java.util.List;
26 | import javax.swing.DefaultComboBoxModel;
27 | import javax.swing.JCheckBoxMenuItem;
28 | import javax.swing.JMenuItem;
29 | import javax.swing.SwingWorker;
30 | import org.apache.logging.log4j.LogManager;
31 | import org.apache.logging.log4j.Logger;
32 |
33 | /**
34 | * TLS-Scanner.
35 | *
36 | * @author Nurullah Erinola
37 | */
38 | public class UIScanner extends javax.swing.JPanel implements IContextMenuFactory {
39 |
40 | private static final Logger LOGGER = LogManager.getLogger(UIScanner.class.getName());
41 | private UIScanHistory scanHistory;
42 |
43 | /**
44 | * Creates new form UIScanner.
45 | */
46 | public UIScanner(UIScanHistory scanHistory) {
47 | initComponents();
48 | initJComboBoxes();
49 | this.scanHistory = scanHistory;
50 | }
51 |
52 | /**
53 | * This method is called from within the constructor to initialize the form.
54 | * WARNING: Do NOT modify this code. The content of this method is always
55 | * regenerated by the Form Editor.
56 | */
57 | @SuppressWarnings("unchecked")
58 | // //GEN-BEGIN:initComponents
59 | private void initComponents() {
60 |
61 | jButtonScan = new javax.swing.JButton();
62 | jTextFieldHost = new javax.swing.JTextField();
63 | jLabel1 = new javax.swing.JLabel();
64 | jLabel3 = new javax.swing.JLabel();
65 | jButtonCopy = new javax.swing.JButton();
66 | jLabel2 = new javax.swing.JLabel();
67 | jLabel4 = new javax.swing.JLabel();
68 | jLabel5 = new javax.swing.JLabel();
69 | jLabel6 = new javax.swing.JLabel();
70 | jLabel7 = new javax.swing.JLabel();
71 | jTextFieldParallelProbes = new javax.swing.JTextField();
72 | jTextFieldOverallThreads = new javax.swing.JTextField();
73 | jComboBoxDangerLevel = new javax.swing.JComboBox<>();
74 | jComboBoxReportDetail = new javax.swing.JComboBox<>();
75 | jComboBoxScanDetail = new javax.swing.JComboBox<>();
76 | jCheckBoxNoColor = new javax.swing.JCheckBox();
77 | jCheckBoxDefaultSetting = new javax.swing.JCheckBox();
78 | jScrollPaneResult = new javax.swing.JScrollPane();
79 | jTextPaneResult = new javax.swing.JTextPane();
80 | jCheckBoxStarTls = new javax.swing.JCheckBox();
81 | jComboBoxStarTLS = new javax.swing.JComboBox<>();
82 | jLabel8 = new javax.swing.JLabel();
83 | jTextFieldTimeout = new javax.swing.JTextField();
84 |
85 | jButtonScan.setText("Scan");
86 | jButtonScan.addActionListener(new java.awt.event.ActionListener() {
87 | public void actionPerformed(java.awt.event.ActionEvent evt) {
88 | jButtonScanActionPerformed(evt);
89 | }
90 | });
91 |
92 | jTextFieldHost.setText("localhost:4433");
93 | jTextFieldHost.setToolTipText("Who to connect to. Syntax: localhost:4433");
94 |
95 | jLabel1.setText("Host:");
96 |
97 | jLabel3.setText("Result:");
98 |
99 | jButtonCopy.setText("Copy");
100 | jButtonCopy.setToolTipText("Copy report to clipboard.");
101 | jButtonCopy.addActionListener(new java.awt.event.ActionListener() {
102 | public void actionPerformed(java.awt.event.ActionEvent evt) {
103 | jButtonCopyActionPerformed(evt);
104 | }
105 | });
106 |
107 | jLabel2.setText("Parallel Probes:");
108 | jLabel2.setToolTipText("Defines the number of threads responsible for different TLS probes. If set to 1, only one specific TLS probe (e.g., TLS version scan) can be run in time.");
109 |
110 | jLabel4.setText("Overall Threads:");
111 | jLabel4.setToolTipText("The maximum number of threads used to execute TLS probes located in the scanning queue. This is also the maximum number of threads communicating with the analyzed server.");
112 |
113 | jLabel5.setText("Danger Level:");
114 | jLabel5.setToolTipText("How aggressive the Scanner should test");
115 |
116 | jLabel6.setText("Scan Detail:");
117 | jLabel6.setToolTipText("How detailed do you want to scan.");
118 |
119 | jLabel7.setText("Report Detail:");
120 | jLabel7.setToolTipText("How detailed do you want the report to be.");
121 |
122 | jTextFieldParallelProbes.setText("4");
123 | jTextFieldParallelProbes.setToolTipText("Enter only numbers.");
124 | jTextFieldParallelProbes.setEnabled(false);
125 |
126 | jTextFieldOverallThreads.setText("100");
127 | jTextFieldOverallThreads.setToolTipText("Enter only numbers.");
128 | jTextFieldOverallThreads.setEnabled(false);
129 |
130 | jComboBoxDangerLevel.setEnabled(false);
131 |
132 | jComboBoxReportDetail.setEnabled(false);
133 |
134 | jComboBoxScanDetail.setEnabled(false);
135 |
136 | jCheckBoxNoColor.setText("No color");
137 | jCheckBoxNoColor.setToolTipText("If you don't want colored text.");
138 |
139 | jCheckBoxDefaultSetting.setSelected(true);
140 | jCheckBoxDefaultSetting.setText("Use default settings");
141 | jCheckBoxDefaultSetting.addActionListener(new java.awt.event.ActionListener() {
142 | public void actionPerformed(java.awt.event.ActionEvent evt) {
143 | jCheckBoxDefaultSettingActionPerformed(evt);
144 | }
145 | });
146 |
147 | jTextPaneResult.setEditable(false);
148 | jTextPaneResult.setFont(new java.awt.Font("Monospaced", 0, 14)); // NOI18N
149 | jScrollPaneResult.setViewportView(jTextPaneResult);
150 |
151 | jCheckBoxStarTls.setText("Scan STARTTLS:");
152 | jCheckBoxStarTls.addActionListener(new java.awt.event.ActionListener() {
153 | public void actionPerformed(java.awt.event.ActionEvent evt) {
154 | jCheckBoxStarTlsActionPerformed(evt);
155 | }
156 | });
157 |
158 | jComboBoxStarTLS.setEnabled(false);
159 |
160 | jLabel8.setText("Timeout:");
161 | jLabel8.setToolTipText("The timeout used for the scans in ms.");
162 |
163 | jTextFieldTimeout.setText("1000");
164 | jTextFieldTimeout.setToolTipText("Enter only numbers.");
165 | jTextFieldTimeout.setEnabled(false);
166 |
167 | javax.swing.GroupLayout layout = new javax.swing.GroupLayout(this);
168 | this.setLayout(layout);
169 | layout.setHorizontalGroup(
170 | layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
171 | .addGroup(layout.createSequentialGroup()
172 | .addContainerGap()
173 | .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
174 | .addComponent(jScrollPaneResult, javax.swing.GroupLayout.DEFAULT_SIZE, 799, Short.MAX_VALUE)
175 | .addGroup(layout.createSequentialGroup()
176 | .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING, false)
177 | .addGroup(layout.createSequentialGroup()
178 | .addComponent(jLabel3)
179 | .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
180 | .addComponent(jButtonCopy))
181 | .addComponent(jButtonScan, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
182 | .addGroup(layout.createSequentialGroup()
183 | .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
184 | .addComponent(jLabel2)
185 | .addComponent(jLabel6)
186 | .addComponent(jLabel5)
187 | .addComponent(jLabel1))
188 | .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
189 | .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
190 | .addComponent(jTextFieldHost, javax.swing.GroupLayout.PREFERRED_SIZE, 525, javax.swing.GroupLayout.PREFERRED_SIZE)
191 | .addGroup(layout.createSequentialGroup()
192 | .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING, false)
193 | .addComponent(jComboBoxScanDetail, 0, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
194 | .addComponent(jComboBoxDangerLevel, javax.swing.GroupLayout.PREFERRED_SIZE, 118, javax.swing.GroupLayout.PREFERRED_SIZE)
195 | .addComponent(jTextFieldParallelProbes, javax.swing.GroupLayout.Alignment.TRAILING))
196 | .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED)
197 | .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
198 | .addComponent(jLabel4)
199 | .addComponent(jLabel7)
200 | .addComponent(jLabel8))
201 | .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
202 | .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.TRAILING, false)
203 | .addComponent(jTextFieldTimeout, javax.swing.GroupLayout.Alignment.LEADING)
204 | .addComponent(jComboBoxReportDetail, 0, 118, Short.MAX_VALUE)
205 | .addComponent(jTextFieldOverallThreads)))
206 | .addGroup(layout.createSequentialGroup()
207 | .addComponent(jCheckBoxDefaultSetting)
208 | .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED)
209 | .addComponent(jCheckBoxNoColor))
210 | .addGroup(layout.createSequentialGroup()
211 | .addComponent(jCheckBoxStarTls)
212 | .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
213 | .addComponent(jComboBoxStarTLS, javax.swing.GroupLayout.PREFERRED_SIZE, 118, javax.swing.GroupLayout.PREFERRED_SIZE)))))
214 | .addGap(0, 0, Short.MAX_VALUE)))
215 | .addContainerGap())
216 | );
217 | layout.setVerticalGroup(
218 | layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
219 | .addGroup(layout.createSequentialGroup()
220 | .addContainerGap()
221 | .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
222 | .addComponent(jLabel1)
223 | .addComponent(jTextFieldHost, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE))
224 | .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
225 | .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
226 | .addComponent(jCheckBoxDefaultSetting)
227 | .addComponent(jCheckBoxNoColor))
228 | .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
229 | .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
230 | .addComponent(jCheckBoxStarTls)
231 | .addComponent(jComboBoxStarTLS, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE))
232 | .addGap(18, 18, 18)
233 | .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
234 | .addComponent(jLabel2)
235 | .addComponent(jTextFieldParallelProbes, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
236 | .addComponent(jTextFieldOverallThreads, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
237 | .addComponent(jLabel4))
238 | .addGap(9, 9, 9)
239 | .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
240 | .addComponent(jComboBoxScanDetail, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
241 | .addComponent(jLabel6)
242 | .addComponent(jLabel7)
243 | .addComponent(jComboBoxReportDetail, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE))
244 | .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED)
245 | .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
246 | .addComponent(jComboBoxDangerLevel, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
247 | .addComponent(jLabel5)
248 | .addComponent(jLabel8)
249 | .addComponent(jTextFieldTimeout, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE))
250 | .addGap(19, 19, 19)
251 | .addComponent(jButtonScan)
252 | .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
253 | .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
254 | .addComponent(jLabel3)
255 | .addComponent(jButtonCopy))
256 | .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
257 | .addComponent(jScrollPaneResult, javax.swing.GroupLayout.DEFAULT_SIZE, 185, Short.MAX_VALUE)
258 | .addContainerGap())
259 | );
260 | }// //GEN-END:initComponents
261 |
262 | private void initJComboBoxes() {
263 | // Init jComboBox for STARTLS protocol selection
264 | ArrayList list = new ArrayList<>();
265 | list.add(StarttlsType.FTP.toString());
266 | list.add(StarttlsType.IMAP.toString());
267 | list.add(StarttlsType.POP3.toString());
268 | list.add(StarttlsType.SMTP.toString());
269 | jComboBoxStarTLS.setModel(new DefaultComboBoxModel(list.toArray()));
270 | // Init jComboBox for Scan Detail and Report Detail
271 | list = new ArrayList<>();
272 | list.add(ScannerDetail.ALL.toString());
273 | list.add(ScannerDetail.DETAILED.toString());
274 | list.add(ScannerDetail.NORMAL.toString());
275 | list.add(ScannerDetail.QUICK.toString());
276 | jComboBoxScanDetail.setModel(new DefaultComboBoxModel(list.toArray()));
277 | jComboBoxScanDetail.setSelectedIndex(2);
278 | jComboBoxReportDetail.setModel(new DefaultComboBoxModel(list.toArray()));
279 | jComboBoxReportDetail.setSelectedIndex(2);
280 | // Init jComboBox for Danger Level
281 | list = new ArrayList<>();
282 | for(int i = 1; i <= 10; i++) {
283 | list.add(String.valueOf(i));
284 | }
285 | jComboBoxDangerLevel.setModel(new DefaultComboBoxModel(list.toArray()));
286 | jComboBoxDangerLevel.setSelectedIndex(9);
287 | }
288 |
289 | /**
290 | * Add new menu item to context menu.
291 | */
292 | @Override
293 | public List createMenuItems(IContextMenuInvocation contextMenuInvocation) {
294 | List menuList = new ArrayList<>();
295 | JMenuItem jMenuItemSendToScanner = new JCheckBoxMenuItem("Send to TLS-Scanner");
296 | jMenuItemSendToScanner.addActionListener(new ActionListener() {
297 | @Override
298 | public void actionPerformed(java.awt.event.ActionEvent evt) {
299 | // Set selected Host
300 | jTextFieldHost.setText(contextMenuInvocation.getSelectedMessages()[0].getHttpService().getHost());
301 | }
302 | });
303 | menuList.add(jMenuItemSendToScanner);
304 | return menuList;
305 | }
306 |
307 | /**
308 | * Check user inputs.
309 | * @return True if checks failed.
310 | */
311 | private boolean checkInputs() {
312 | boolean checkFailed = false;
313 | jTextPaneResult.setText("");
314 | // check Host
315 | if(jTextFieldHost.getText() == null) {
316 | jTextPaneResult.setText(jTextPaneResult.getText() + "-Could not parse provided host: " + jTextFieldHost.getText() + "\n");
317 | checkFailed = true;
318 | } else {
319 | String[] parsedHost = jTextFieldHost.getText().split(":");
320 | switch (parsedHost.length) {
321 | case 1:
322 | break;
323 | case 2:
324 | if(parsedHost[1].matches("[0-9]+")) {
325 | int port = Integer.parseInt(parsedHost[1]);
326 | if (port >= 0 && port <= 65535) {
327 | break;
328 | }
329 | }
330 | jTextPaneResult.setText(jTextPaneResult.getText() + "-Port must be in interval [0,65535], but is " + parsedHost[1] + "\n");
331 | checkFailed = true;
332 | break;
333 | default:
334 | jTextPaneResult.setText(jTextPaneResult.getText() + "-Could not parse provided host: " + jTextFieldHost.getText() + "\n");
335 | checkFailed = true;
336 | break;
337 | }
338 | }
339 | if(!jCheckBoxDefaultSetting.isSelected()) {
340 | // check ParallelProbes, OverallThreads, Timeout
341 | if(!jTextFieldParallelProbes.getText().matches("[0-9]+")) {
342 | jTextPaneResult.setText(jTextPaneResult.getText() + "-Parallel Probes input is not a number or empty\n");
343 | checkFailed = true;
344 | }
345 | if(!jTextFieldOverallThreads.getText().matches("[0-9]+")) {
346 | jTextPaneResult.setText(jTextPaneResult.getText() + "-Overall Threads input is not a number or empty\n");
347 | checkFailed = true;
348 | }
349 | if(!jTextFieldTimeout.getText().matches("[0-9]+")) {
350 | jTextPaneResult.setText(jTextPaneResult.getText() + "-Timeout input is not a number or empty\n");
351 | checkFailed = true;
352 | }
353 | }
354 | return checkFailed;
355 | }
356 |
357 | private void jButtonScanActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_jButtonScanActionPerformed
358 | // Check user inputs
359 | if(checkInputs()) {
360 | return;
361 | }
362 | // Create config
363 | ScannerConfig config = new ScannerConfig(new GeneralDelegate());
364 | config.getClientDelegate().setHost(jTextFieldHost.getText());
365 | config.setNoColor(jCheckBoxNoColor.isSelected());
366 | config.setParallelProbes(4);
367 | config.setOverallThreads(100);
368 | config.setTimeout(1000);
369 | if(!jCheckBoxDefaultSetting.isSelected()) {
370 | config.setDangerLevel(Integer.parseInt((String) jComboBoxDangerLevel.getSelectedItem()));
371 | config.setParallelProbes(Integer.parseInt(jTextFieldParallelProbes.getText()));
372 | config.setOverallThreads(Integer.parseInt(jTextFieldOverallThreads.getText()));
373 | config.setTimeout(Integer.parseInt(jTextFieldTimeout.getText()));
374 | config.setReportDetail(ScannerDetail.valueOf((String) jComboBoxReportDetail.getSelectedItem()));
375 | config.setScanDetail(ScannerDetail.valueOf((String) jComboBoxScanDetail.getSelectedItem()));
376 | }
377 | if(jCheckBoxStarTls.isSelected()) {
378 | config.getStarttlsDelegate().setStarttlsType(StarttlsType.valueOf((String) jComboBoxStarTLS.getSelectedItem()));
379 | }
380 | // Clarify scan start
381 | jTextPaneResult.setStyledDocument(ANSIHelper.getStyledDocument("Scanning " + config.getClientDelegate().getHost() + " - please be patient..."));
382 | jButtonScan.setEnabled(false);
383 | // Use SwingWorker to execute scan in backround
384 | SwingWorker worker = new SwingWorker() {
385 | SiteReport report;
386 |
387 | @Override
388 | protected Boolean doInBackground() throws Exception {
389 | LOGGER.info("---------- Start scanning of {} ----------", config.getClientDelegate().getHost());
390 | // Init scanner and start scan
391 | TlsScanner scanner = new TlsScanner(config);
392 | report = scanner.scan();
393 | return true;
394 | }
395 | @Override
396 | protected void done() {
397 | LOGGER.info("---------- Scan of {} finished ----------", config.getClientDelegate().getHost());
398 | jButtonScan.setEnabled(true);
399 | // Print scan result
400 | if(report != null) {
401 | String fullReport = report.getFullReport(config.getReportDetail(), !config.isNoColor());
402 | jTextPaneResult.setStyledDocument(ANSIHelper.getStyledDocument(fullReport));
403 | jTextPaneResult.setCaretPosition(0);
404 | // Send config and report to scan history
405 | scanHistory.add(config, report);
406 | } else {
407 | jTextPaneResult.setStyledDocument(ANSIHelper.getStyledDocument("Scan of " + config.getClientDelegate().getHost() + " failed..."));
408 | }
409 | }
410 | };
411 | worker.execute();
412 | }//GEN-LAST:event_jButtonScanActionPerformed
413 |
414 | private void jButtonCopyActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_jButtonCopyActionPerformed
415 | String toCopy = jTextPaneResult.getText();
416 | StringSelection stringSelection = new StringSelection(toCopy);
417 | Clipboard clpbrd = Toolkit.getDefaultToolkit().getSystemClipboard();
418 | clpbrd.setContents(stringSelection, null);
419 | }//GEN-LAST:event_jButtonCopyActionPerformed
420 |
421 | private void jCheckBoxDefaultSettingActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_jCheckBoxDefaultSettingActionPerformed
422 | if(jCheckBoxDefaultSetting.isSelected()) {
423 | jComboBoxDangerLevel.setEnabled(false);
424 | jComboBoxReportDetail.setEnabled(false);
425 | jComboBoxScanDetail.setEnabled(false);
426 | jTextFieldOverallThreads.setEnabled(false);
427 | jTextFieldParallelProbes.setEnabled(false);
428 | jTextFieldTimeout.setEnabled(false);
429 | } else {
430 | jComboBoxDangerLevel.setEnabled(true);
431 | jComboBoxReportDetail.setEnabled(true);
432 | jComboBoxScanDetail.setEnabled(true);
433 | jTextFieldOverallThreads.setEnabled(true);
434 | jTextFieldParallelProbes.setEnabled(true);
435 | jTextFieldTimeout.setEnabled(true);
436 | }
437 | }//GEN-LAST:event_jCheckBoxDefaultSettingActionPerformed
438 |
439 | private void jCheckBoxStarTlsActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_jCheckBoxStarTlsActionPerformed
440 | if(jCheckBoxStarTls.isSelected()) {
441 | jComboBoxStarTLS.setEnabled(true);
442 | } else {
443 | jComboBoxStarTLS.setEnabled(false);
444 | }
445 | }//GEN-LAST:event_jCheckBoxStarTlsActionPerformed
446 |
447 |
448 | // Variables declaration - do not modify//GEN-BEGIN:variables
449 | private javax.swing.JButton jButtonCopy;
450 | private javax.swing.JButton jButtonScan;
451 | private javax.swing.JCheckBox jCheckBoxDefaultSetting;
452 | private javax.swing.JCheckBox jCheckBoxNoColor;
453 | private javax.swing.JCheckBox jCheckBoxStarTls;
454 | private javax.swing.JComboBox jComboBoxDangerLevel;
455 | private javax.swing.JComboBox jComboBoxReportDetail;
456 | private javax.swing.JComboBox jComboBoxScanDetail;
457 | private javax.swing.JComboBox jComboBoxStarTLS;
458 | private javax.swing.JLabel jLabel1;
459 | private javax.swing.JLabel jLabel2;
460 | private javax.swing.JLabel jLabel3;
461 | private javax.swing.JLabel jLabel4;
462 | private javax.swing.JLabel jLabel5;
463 | private javax.swing.JLabel jLabel6;
464 | private javax.swing.JLabel jLabel7;
465 | private javax.swing.JLabel jLabel8;
466 | private javax.swing.JScrollPane jScrollPaneResult;
467 | private javax.swing.JTextField jTextFieldHost;
468 | private javax.swing.JTextField jTextFieldOverallThreads;
469 | private javax.swing.JTextField jTextFieldParallelProbes;
470 | private javax.swing.JTextField jTextFieldTimeout;
471 | private javax.swing.JTextPane jTextPaneResult;
472 | // End of variables declaration//GEN-END:variables
473 | }
474 |
--------------------------------------------------------------------------------
/src/main/java/de/rub/nds/burp/tlsattacker/gui/UITab.java:
--------------------------------------------------------------------------------
1 | /**
2 | * TLS-Attacker-BurpExtension
3 | *
4 | * Copyright 2018 Ruhr University Bochum / Hackmanit GmbH
5 | *
6 | * Licensed under Apache License 2.0
7 | * http://www.apache.org/licenses/LICENSE-2.0/
8 | */
9 | package de.rub.nds.burp.tlsattacker.gui;
10 |
11 | import burp.IBurpExtenderCallbacks;
12 | import burp.ITab;
13 |
14 | /**
15 | * An additional tab in Burp Suite.
16 | *
17 | * @author Nurullah Erinola
18 | */
19 | public class UITab implements ITab {
20 |
21 | private UIMain main;
22 | private final IBurpExtenderCallbacks callbacks;
23 |
24 | /**
25 | * Create a new Tab.
26 | * @param callbacks
27 | */
28 | public UITab(IBurpExtenderCallbacks callbacks) {
29 | this.callbacks = callbacks;
30 | this.main = new UIMain(callbacks);
31 | callbacks.customizeUiComponent(main);
32 | callbacks.addSuiteTab(this);
33 | }
34 |
35 | /**
36 | * @return Get the UI component that should be registered at the Burp Suite GUI.
37 | */
38 | @Override
39 | public UIMain getUiComponent() {
40 | return main;
41 | }
42 |
43 | /**
44 | * @return Get the headline for the Tab.
45 | */
46 | @Override
47 | public String getTabCaption() {
48 | return "TLS-Attacker";
49 | }
50 |
51 | }
52 |
--------------------------------------------------------------------------------
/src/main/java/de/rub/nds/burp/utilities/ANSIHelper.java:
--------------------------------------------------------------------------------
1 | /**
2 | * TLS-Attacker-BurpExtension
3 | *
4 | * Copyright 2018 Ruhr University Bochum / Hackmanit GmbH
5 | *
6 | * Licensed under Apache License 2.0
7 | * http://www.apache.org/licenses/LICENSE-2.0/
8 | */
9 | package de.rub.nds.burp.utilities;
10 |
11 | import de.rub.nds.tlsscanner.constants.AnsiColor;
12 | import java.awt.Color;
13 | import javax.swing.text.BadLocationException;
14 | import javax.swing.text.DefaultStyledDocument;
15 | import javax.swing.text.SimpleAttributeSet;
16 | import javax.swing.text.StyleConstants;
17 | import javax.swing.text.StyledDocument;
18 | import org.apache.commons.lang3.StringUtils;
19 |
20 | /**
21 | * Printer for the SiteReport.
22 | *
23 | * @author Nurullah Erinola
24 | */
25 | public class ANSIHelper {
26 |
27 | // self defined colors
28 | private static final Color LIGHT_ORANGE = new Color(255, 153, 0);
29 | private static final Color DARK_RED = new Color(204, 0, 0);
30 | private static final Color DARK_BLUE = new Color(0, 0, 204);
31 | private static final Color DARK_GREEN = new Color(0, 153, 0);
32 | private static final Color DARK_VIOLET = new Color(148,0,211);
33 |
34 | private static final String ANSI_START = "\u001B[";
35 | private static final String ANSI_END = "m";
36 |
37 | public static StyledDocument getStyledDocument(String report) {
38 | StyledDocument document = new DefaultStyledDocument();
39 | SimpleAttributeSet attributes = new SimpleAttributeSet();
40 |
41 | int currentPos = 0; // current char position in report
42 | int startIndex = 0; // start of escape sequence
43 | int endIndex = 0; // end of escape sequence
44 |
45 | String tmp = "";
46 |
47 | if (report.length() > 0) {
48 | // Search start of escape sequence
49 | startIndex = report.indexOf(ANSI_START);
50 | // No escape sequence found, print all
51 | if (startIndex == -1) {
52 | append(document, attributes, report);
53 | return document;
54 | }
55 | // Escape sequence is not first char, print all text to escape sequence
56 | if (startIndex > 0) {
57 | tmp = report.substring(0, startIndex);
58 | document = append(document, attributes, tmp);
59 | currentPos = startIndex;
60 | }
61 |
62 | while (true) {
63 | // Search the end of the escape sequence
64 | endIndex = report.indexOf(ANSI_END, currentPos);
65 |
66 | // End of escape sequence not found, print all
67 | if (endIndex == -1) {
68 | document = append(document, attributes, report.substring(currentPos, report.length()));
69 | break;
70 | // End of escape sequence found, parse
71 | } else {
72 | tmp = report.substring(currentPos, endIndex+1);
73 | attributes = parseAndAdd(attributes, tmp);
74 | currentPos = endIndex+1;
75 | }
76 |
77 | // Search start of next escape sequence
78 | startIndex = report.indexOf(ANSI_START, currentPos);
79 |
80 | // No further escape sequence available, print all
81 | if (startIndex == -1) {
82 | document = append(document, attributes, report.substring(currentPos, report.length()));
83 | break;
84 | // Further escape sequence available, print substring between escape sequence
85 | } else {
86 | document = append(document, attributes, report.substring(currentPos, startIndex));
87 | currentPos = startIndex;
88 | }
89 | }
90 | }
91 | return document;
92 | }
93 |
94 | private static String replaceTabs(String string) {
95 | String[] splitted = string.split("\n", -1);
96 | for(int i = 0; i < splitted.length; i++) {
97 | int pos = splitted[i].indexOf("\t");
98 | while(pos != -1) {
99 | splitted[i] = splitted[i].replaceFirst("\t", StringUtils.repeat(" ", 8-(pos%8)));
100 | pos = splitted[i].indexOf("\t");
101 | }
102 | }
103 | return String.join("\n", splitted);
104 | }
105 |
106 | private static StyledDocument append(StyledDocument document, SimpleAttributeSet attributes, String toAppend) {
107 | try {
108 | document.insertString(document.getLength(), replaceTabs(toAppend), attributes);
109 | } catch (BadLocationException exp) {
110 |
111 | }
112 | return document;
113 | }
114 |
115 | private static SimpleAttributeSet parseAndAdd(SimpleAttributeSet attrSet, String ansi) {
116 | switch(AnsiColor.getAnsiColor(ansi)) {
117 | case RESET:
118 | attrSet = new SimpleAttributeSet();
119 | break;
120 | case BLACK:
121 | attrSet.addAttribute(StyleConstants.Foreground, Color.BLACK);
122 | break;
123 | case RED:
124 | attrSet.addAttribute(StyleConstants.Foreground, DARK_RED);
125 | break;
126 | case GREEN:
127 | attrSet.addAttribute(StyleConstants.Foreground, DARK_GREEN);
128 | break;
129 | case YELLOW:
130 | attrSet.addAttribute(StyleConstants.Foreground, LIGHT_ORANGE);
131 | break;
132 | case BLUE:
133 | attrSet.addAttribute(StyleConstants.Foreground, DARK_BLUE);
134 | break;
135 | case PURPLE:
136 | attrSet.addAttribute(StyleConstants.Foreground, DARK_VIOLET);
137 | break;
138 | case CYAN:
139 | attrSet.addAttribute(StyleConstants.Foreground, Color.CYAN);
140 | break;
141 | case WHITE:
142 | attrSet.addAttribute(StyleConstants.Foreground, Color.WHITE);
143 | break;
144 | case BLACK_BACKGROUND:
145 | attrSet.addAttribute(StyleConstants.Background, Color.BLACK);
146 | break;
147 | case RED_BACKGROUND:
148 | attrSet.addAttribute(StyleConstants.Background, DARK_RED);
149 | break;
150 | case GREEN_BACKGROUND:
151 | attrSet.addAttribute(StyleConstants.Background, DARK_GREEN);
152 | break;
153 | case YELLOW_BACKGROUND:
154 | attrSet.addAttribute(StyleConstants.Background, LIGHT_ORANGE);
155 | break;
156 | case BLUE_BACKGROUND:
157 | attrSet.addAttribute(StyleConstants.Background, DARK_BLUE);
158 | break;
159 | case PURPLE_BACKGROUND:
160 | attrSet.addAttribute(StyleConstants.Background, DARK_VIOLET);
161 | break;
162 | case CYAN_BACKGROUND:
163 | attrSet.addAttribute(StyleConstants.Background, Color.CYAN);
164 | break;
165 | case WHITE_BACKGROUND:
166 | attrSet.addAttribute(StyleConstants.Background, Color.WHITE);
167 | break;
168 | case BOLD:
169 | attrSet.addAttribute(StyleConstants.CharacterConstants.Bold, Boolean.TRUE);
170 | break;
171 | case UNDERLINE:
172 | StyleConstants.setUnderline(attrSet, true);
173 | break;
174 | default:
175 | break;
176 | }
177 | return attrSet;
178 | }
179 | }
180 |
--------------------------------------------------------------------------------
/src/main/java/de/rub/nds/burp/utilities/table/TableEntry.java:
--------------------------------------------------------------------------------
1 | /**
2 | * TLS-Attacker-BurpExtension
3 | *
4 | * Copyright 2018 Ruhr University Bochum / Hackmanit GmbH
5 | *
6 | * Licensed under Apache License 2.0
7 | * http://www.apache.org/licenses/LICENSE-2.0/
8 | */
9 | package de.rub.nds.burp.utilities.table;
10 |
11 | import de.rub.nds.tlsscanner.config.ScannerConfig;
12 | import de.rub.nds.tlsscanner.report.SiteReport;
13 |
14 | /**
15 | * A table entry for the class Table.
16 | *
17 | * @author Nurullah Erinola
18 | */
19 | public class TableEntry {
20 |
21 | private ScannerConfig config;
22 | private SiteReport report;
23 | private String counter;
24 | private String host;
25 | private String danger;
26 | private String noColor;
27 | private String scanDetail;
28 | private String reportDetail;
29 | private String starTls;
30 |
31 | /**
32 | * Construct a new table entry.
33 | */
34 | public TableEntry(int counter, SiteReport report, ScannerConfig config) {
35 | this.report = report;
36 | this.config = config;
37 | this.host = report.getHost();
38 | this.counter = Integer.toString(counter);
39 | this.danger = Integer.toString(config.getDangerLevel());
40 | this.noColor = Boolean.toString(config.isNoColor());
41 | this.scanDetail = config.getScanDetail().toString();
42 | this.reportDetail = config.getReportDetail().toString();
43 | this.starTls = config.getStarttlsDelegate().getStarttlsType().toString();
44 | }
45 |
46 | public SiteReport getSiteReport() {
47 | return report;
48 | }
49 |
50 | public ScannerConfig getConfig() {
51 | return config;
52 | }
53 |
54 | public String getCounter() {
55 | return counter;
56 | }
57 |
58 | public String getHost() {
59 | return host;
60 | }
61 |
62 | public String getDanger() {
63 | return danger;
64 | }
65 |
66 | public String getNoColor() {
67 | return noColor;
68 | }
69 |
70 | public String getScanDetail() {
71 | return scanDetail;
72 | }
73 |
74 | public String getReportDetail() {
75 | return reportDetail;
76 | }
77 |
78 | public String getStarTls() {
79 | return starTls;
80 | }
81 | }
82 |
--------------------------------------------------------------------------------
/src/main/java/de/rub/nds/burp/utilities/table/TableModel.java:
--------------------------------------------------------------------------------
1 | /**
2 | * TLS-Attacker-BurpExtension
3 | *
4 | * Copyright 2018 Ruhr University Bochum / Hackmanit GmbH
5 | *
6 | * Licensed under Apache License 2.0
7 | * http://www.apache.org/licenses/LICENSE-2.0/
8 | */
9 | package de.rub.nds.burp.utilities.table;
10 |
11 | import java.util.ArrayList;
12 | import javax.swing.table.AbstractTableModel;
13 |
14 | /**
15 | * Helper class for the class Table.
16 | *
17 | * @author Nurullah Erinola
18 | */
19 | public class TableModel extends AbstractTableModel{
20 |
21 | private ArrayList list;
22 | private String[] columnNames = {"#", "Host", "Scan Detail", "Report Detail", "Danger Level", "STARTLS", "No color"};
23 |
24 | /**
25 | * Construct a new Table Helper
26 | */
27 | public TableModel() {
28 | list = new ArrayList<>();
29 | }
30 |
31 | /**
32 | * Get the table list.
33 | * @return The list saved during the construction.
34 | */
35 | public ArrayList getTableList(){
36 | return list;
37 | }
38 |
39 | /**
40 | * Add a row to the list and the table.
41 | * @param entry The new row.
42 | */
43 | public void addRow(TableEntry entry){
44 | list.add(entry);
45 | int tmp = list.size()-1;
46 | fireTableRowsInserted(tmp, tmp);
47 | }
48 |
49 | /**
50 | * Remove all entries from the table list.
51 | */
52 | public void clear(){
53 | list.clear();
54 | fireTableDataChanged();
55 | }
56 |
57 | /**
58 | * Get the number of rows.
59 | * @return Number of rows.
60 | */
61 | @Override
62 | public int getRowCount()
63 | {
64 | return list.size();
65 | }
66 |
67 | /**
68 | *
69 | * @return Number of columns.
70 | */
71 | @Override
72 | public int getColumnCount()
73 | {
74 | return columnNames.length;
75 | }
76 |
77 | /**
78 | * Get the name of the column.
79 | * @param columnIndex Index of the column.
80 | * @return The name of the column.
81 | */
82 | @Override
83 | public String getColumnName(int columnIndex)
84 | {
85 | return columnNames[columnIndex];
86 | }
87 |
88 | /**
89 | * Get the class of the column.
90 | * @param columnIndex Index of the column.
91 | * @return The class of the column.
92 | */
93 | @Override
94 | public Class> getColumnClass(int columnIndex)
95 | {
96 | return String.class;
97 | }
98 |
99 | /**
100 | * Get the value at a position.
101 | * @param rowIndex The row.
102 | * @param columnIndex The column.
103 | * @return Value for the specified entry. Null if not found.
104 | */
105 | @Override
106 | public Object getValueAt(int rowIndex, int columnIndex)
107 | {
108 | TableEntry entry = list.get(rowIndex);
109 |
110 | switch (columnIndex)
111 | {
112 | case 0:
113 | return entry.getCounter();
114 | case 1:
115 | return entry.getHost();
116 | case 2:
117 | return entry.getScanDetail();
118 | case 3:
119 | return entry.getReportDetail();
120 | case 4:
121 | return entry.getDanger();
122 | case 5:
123 | return entry.getStarTls();
124 | case 6:
125 | return entry.getNoColor();
126 | default:
127 | return null;
128 | }
129 | }
130 |
131 | @Override
132 | public boolean isCellEditable(int rowIndex, int columnIndex) {
133 | return false;
134 | }
135 | }
136 |
--------------------------------------------------------------------------------
/src/main/resources/de.rub.nds.burp.tlsattacker.log4j2.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
9 |
10 |
13 |
14 |
15 |
16 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
31 |
32 |
33 |
34 |
--------------------------------------------------------------------------------