コード例 #1
0
ファイル: NammuView.py プロジェクト: oracc/nammu
 def addCenterPane(self, atfAreaView, consoleView):
     splitPane = JSplitPane(JSplitPane.VERTICAL_SPLIT)
     splitPane.setTopComponent(atfAreaView)
     splitPane.setBottomComponent(consoleView)
     splitPane.setDividerSize(5)
     self.getContentPane().add(splitPane, BorderLayout.CENTER)
     # Make console's high remain smaller compared to edit area
     splitPane.setResizeWeight(0.9)
コード例 #2
0
ファイル: NammuView.py プロジェクト: willismonroe/nammu
 def addCenterPane(self, atfAreaView, consoleView):
     splitPane = JSplitPane(JSplitPane.VERTICAL_SPLIT)
     splitPane.setTopComponent(atfAreaView)
     splitPane.setBottomComponent(consoleView)
     splitPane.setDividerSize(5)
     self.getContentPane().add(splitPane, BorderLayout.CENTER)
     # Make console's high remain smaller compared to edit area
     splitPane.setResizeWeight(0.9)
コード例 #3
0
    def registerExtenderCallbacks(self, callbacks):

        # set our extension name
        callbacks.setExtensionName("Hello world extension")

        # obtain our output and error streams
        stdout = PrintWriter(callbacks.getStdout(), True)
        stderr = PrintWriter(callbacks.getStderr(), True)

        # write a message to our output stream
        stdout.println("Hello output")

        # write a message to our error stream
        stderr.println("Hello errors")

        # write a message to the Burp alerts tab
        callbacks.issueAlert("Hello alerts")

        #create and populate a jtable:
        initial_row = [
            'http', 'www.meetup.com',
            'PyMNtos-Twin-Cities-Python-User-Group/events/267977020/', '', '',
            ''
        ]
        self.fileTable = JTable(ResourceTableModel(initial_row))
        # set up the Tab:

        self.infoPanel = JPanel()
        footerPanel = JPanel()

        footerPanel.add(JLabel("by mcgyver5 "))
        self._chooseFileButton = JButton("OPEN Local FILE",
                                         actionPerformed=self.fileButtonClick)
        self.infoPanel.add(JLabel("INFORMATION PANE"))

        self.infoPanel.add(self._chooseFileButton)
        scrollpane = JScrollPane(self.fileTable)
        ## this is a split inside the top component
        topPane = JSplitPane(JSplitPane.VERTICAL_SPLIT)
        topPane.setTopComponent(self.infoPanel)
        topPane.setBottomComponent(scrollpane)
        self._chooseFileButton.setEnabled(True)
        self._splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT)
        self._splitpane.setTopComponent(topPane)
        self._splitpane.setBottomComponent(footerPanel)
        callbacks.addSuiteTab(self)
コード例 #4
0
ファイル: warstory.py プロジェクト: mcgyver5/warstory
    def registerExtenderCallbacks(self, callbacks):

        # set our extension name
        callbacks.setExtensionName("War Story")

        # obtain our output stream
        self._stdout = PrintWriter(callbacks.getStdout(), True)

        # write a message to our output stream
        self._stdout.println("Loading WarStory")

        # write a message to the Burp alerts tab
        callbacks.issueAlert("Hello alerts")
        label = JLabel("INFO PANEL")
        self.infoPanel = JPanel()
        footerPanel = JPanel()
        footerPanel.add(JLabel("by Tim mcgyver5 McGuire"))
        self._chooseFileButton = JButton("OPEN WAR FILE",
                                         actionPerformed=self.fileButtonClick)
        self.infoPanel.add(JLabel("THIS IS INFORMATION PANE"))
        self.infoPanel.add(self._chooseFileButton)
        # iaap.war|web.xml|axServlet|/skuppy/axservlet.do|
        self._chooseFileButton.setEnabled(True)
        initial_row = ['a', 'bb', 'ccc', 'ddd', 'eeee']
        self.fileTable = JTable(ResourceTableModel(initial_row))
        scrollpane = JScrollPane(self.fileTable)

        ## this is a split inside the top component
        topPane = JSplitPane(JSplitPane.VERTICAL_SPLIT)

        topPane.setTopComponent(self.infoPanel)
        topPane.setBottomComponent(scrollpane)

        # split the top panel into a Panel and a JScrollPane

        self._splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT)
        self._splitpane.setTopComponent(topPane)
        self._splitpane.setBottomComponent(footerPanel)

        callbacks.addSuiteTab(self)
コード例 #5
0
    def registerExtenderCallbacks(self, callbacks):

        # set our extension name
        callbacks.setExtensionName("CT Search")
        callbacks.registerContextMenuFactory(self)
        # obtain output stream
        self._stdout = PrintWriter(callbacks.getStdout(), True)
        stdout = PrintWriter(callbacks.getStdout(), True)

        # write a message to our output stream
        self._callbacks = callbacks

        # write a message to the Burp alerts tab
        callbacks.issueAlert("Hello alerts")

        #create and populate a jtable:
        initial_row = ['a', 'DOMAINS', True]
        self.fileTable = JTable(ResourceTableModel())
        # set up the Tab:

        self.infoPanel = JPanel()
        footerPanel = JPanel()

        footerPanel.add(JLabel("by mcgyver5 "))
        #        self._chooseFileButton = JButton("OPEN Local FILE", actionPerformed=self.fileButtonClick)
        self.infoPanel.add(JLabel("INFORMATION PANE"))

        #        self.infoPanel.add(self._chooseFileButton)
        scrollpane = JScrollPane(self.fileTable)
        ## this is a split inside the top component
        topPane = JSplitPane(JSplitPane.VERTICAL_SPLIT)
        topPane.setTopComponent(self.infoPanel)
        topPane.setBottomComponent(scrollpane)
        #self._chooseFileButton.setEnabled(True)
        self._splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT)
        self._splitpane.setTopComponent(topPane)
        self._splitpane.setBottomComponent(footerPanel)
コード例 #6
0
    def getUiComponent(self):
        self.domainTable = JTable(ResourceTableModel())
        self.domainTable.setRowHeight(30)
        #Delete:
        #jcolumnModel = self.domainTable.getColumnModel()

        splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT)
        topPane = JPanel()
        image_label = HelpLabel(self.callbacks)
        image_label.setHelpIcon("nothing")
        image_label.addMouseListener(ScreenMouseListener(self.callbacks))
        scope_button = JButton("Add Selected Domains To Scope",
                               actionPerformed=self.addToScope)
        dns_button = JButton("Resolve DNS", actionPerformed=self.resolveDns)
        #        search_text = JTextField("")
        saveButton = JButton("Save results", actionPerformed=self.saveResults)
        topPane.add(image_label)
        topPane.add(scope_button)
        topPane.add(dns_button)
        topPane.add(saveButton)
        scrollpane = JScrollPane(self.domainTable)
        splitpane.setTopComponent(topPane)
        splitpane.setBottomComponent(scrollpane)
        return splitpane
コード例 #7
0
class BurpExtender(IBurpExtender, ITab, IContextMenuFactory):
    def registerExtenderCallbacks(self, callbacks):

        # set our extension name
        callbacks.setExtensionName("CT Search")
        callbacks.registerContextMenuFactory(self)
        # obtain output stream
        self._stdout = PrintWriter(callbacks.getStdout(), True)
        stdout = PrintWriter(callbacks.getStdout(), True)

        # write a message to our output stream
        self._callbacks = callbacks

        # write a message to the Burp alerts tab
        callbacks.issueAlert("Hello alerts")

        #create and populate a jtable:
        initial_row = ['a', 'DOMAINS', True]
        self.fileTable = JTable(ResourceTableModel())
        # set up the Tab:

        self.infoPanel = JPanel()
        footerPanel = JPanel()

        footerPanel.add(JLabel("by mcgyver5 "))
        #        self._chooseFileButton = JButton("OPEN Local FILE", actionPerformed=self.fileButtonClick)
        self.infoPanel.add(JLabel("INFORMATION PANE"))

        #        self.infoPanel.add(self._chooseFileButton)
        scrollpane = JScrollPane(self.fileTable)
        ## this is a split inside the top component
        topPane = JSplitPane(JSplitPane.VERTICAL_SPLIT)
        topPane.setTopComponent(self.infoPanel)
        topPane.setBottomComponent(scrollpane)
        #self._chooseFileButton.setEnabled(True)
        self._splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT)
        self._splitpane.setTopComponent(topPane)
        self._splitpane.setBottomComponent(footerPanel)
        #callbacks.addSuiteTab(self)

    def get_domains_from_json_list(self, json_list):
        my_domain_list = []
        for cert in json_list:
            try:
                domainList = str(cert.get('name_value')).strip()
                for domain in domainList.split("\n"):
                    if not domain in my_domain_list:
                        my_domain_list.append(domain)
            except Exception as e:
                print(e)
        my_domain_list.sort()
        return list(set(my_domain_list))

    def get_domains_from_api(self, domain):
        my_domain_list = []
        try:
            api_url = "https://crt.sh/?q=%.{}&output=json".format(domain)
            request = urllib2.urlopen(api_url)
            data = request.read()
            json_list = json.loads(data)
            my_domain_list = self.get_domains_from_json_list(json_list)
        except Exception as e:
            print("error")
            print(e)
        return my_domain_list

    def lookup_ct(self, whatever):
        domain = ""
        http_traffic = self.context.getSelectedMessages()
        for traffic in http_traffic:
            http_service = traffic.getHttpService()
            host = http_service.getHost()
            domain = host.replace('www.', '')
            self._stdout.println(domain)
        domain_list = self.get_domains_from_api(domain)
        ct_tab = CTSearchTab(self._callbacks)
        self._callbacks.addSuiteTab(ct_tab)
        ct_tab.setDomainList(domain_list)

    def fake_lookup_ct(self, whatever):
        domain_list = self.get_domains_from_file()
        ct_tab = CTSearchTab(self._callbacks)
        self._callbacks.addSuiteTab(ct_tab)
        ct_tab.setDomainList(domain_list)

    def createMenuItems(self, context_menu):
        self.context = context_menu
        menu_list = ArrayList()
        menu_list.add(
            JMenuItem("Lookup Domain in CT Logs",
                      actionPerformed=self.lookup_ct))
        menu_list.add(
            JMenuItem("CT LOgs Test get Domains from test file",
                      actionPerformed=self.fake_lookup_ct))
        return menu_list

    def get_domains_from_file(self):
        my_domain_list = []
        fileChooser = JFileChooser()
        result = fileChooser.showOpenDialog(self._splitpane)
        if result == JFileChooser.APPROVE_OPTION:
            f = fileChooser.getSelectedFile()
            fileName = f.getPath()
            self._stdout.println(fileName)
            file_data = open(fileName).read()
            json_list = json.loads(file_data)
            for cert in json_list:
                try:
                    domainList = str(cert.get('name_value')).strip()
                    for domain in domainList.split("\n"):
                        if not domain in my_domain_list:
                            domain = domain.replace("*.", "")
                            my_domain_list.append(domain)
                except Exception as e:
                    self._stdout.println(e)
            my_domain_list.sort()

        return list(set(my_domain_list))


#    def populateTableModel(self,f):
#        domain_list = []
#        num = 0
#        try:
#            path = os.getcwd()
#            self._stdout.println("path is : " + path)
#            fhandle = open(f)
#            file_data = fhandle.read()
#            domain_list = self.get_domains_from_file(file_data)
#            tableModel = self.fileTable.getModel()
#        except Exception as e:
#            self._stdout.println("exception!  ")
#            self._stdout.println(e)
#        for dom in domain_list:
#            num = num + 1
#            row = [str(num),dom,False]
#            tableModel.addRow(row)
#

    def getTabCaption(self):
        return "Import URLs"

    def getUiComponent(self):
        return self._splitpane
コード例 #8
0
class BurpExtender(IBurpExtender, IExtensionStateListener, ITab):
    ext_name = "CompuRacerExtension"
    ext_version = '1.2'
    loaded = True
    t = None

    def registerExtenderCallbacks(self, callbacks):
        Cb(callbacks)
        Cb.callbacks.setExtensionName(self.ext_name)

        try:
            global compuracer_communication_lock

            # option picker item objects (for Java compatibility)
            item1 = {'key': 'item1', 'name': '2'}
            item2 = {'key': 'item2', 'name': '3'}
            item3 = {'key': 'item3', 'name': '4'}
            item4 = {'key': 'item4', 'name': '5'}
            item5 = {'key': 'item5', 'name': '10'}
            item6 = {'key': 'item6', 'name': '15'}
            item7 = {'key': 'item7', 'name': '20'}
            item8 = {'key': 'item8', 'name': '25'}
            item9 = {'key': 'item9', 'name': '50'}
            item10 = {'key': 'item10', 'name': '100'}

            # main splitted pane + top pane
            self._main_splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT)
            self._outer_settings_pane = JPanel(BorderLayout())
            self._settings_pane = JPanel(GridBagLayout())
            c = GridBagConstraints()

            self.label_1 = JLabel("Number of parallel requests:")
            c.fill = GridBagConstraints.NONE
            c.gridx = 0
            c.gridy = 0
            c.insets = Insets(0, 5, 0, 10)
            c.anchor = GridBagConstraints.LINE_START
            self._settings_pane.add(self.label_1, c)

            self.input_parallel_requests = JComboBox([
                Item(item1),
                Item(item2),
                Item(item3),
                Item(item4),
                Item(item5),
                Item(item6),
                Item(item7),
                Item(item8),
                Item(item9),
                Item(item10)
            ])
            self.input_parallel_requests.setSelectedIndex(4)
            self.input_parallel_requests.setToolTipText(
                "Select the number of parallel requests that will be sent")
            self.input_parallel_requests.addActionListener(
                self.change_parallel_requests)
            c.gridx = 1
            c.gridy = 0
            c.insets = Insets(0, 5, 0, 10)
            self._settings_pane.add(self.input_parallel_requests, c)

            self.option_allow_redirects = JCheckBox(
                "Allow redirects", actionPerformed=self.check_allow_redirects)
            self.option_allow_redirects.setToolTipText(
                "Select whether redirect responses are followed")
            c.gridx = 2
            c.gridy = 0
            c.insets = Insets(0, 20, 0, 10)
            self._settings_pane.add(self.option_allow_redirects, c)

            self.option_sync_last_byte = JCheckBox(
                "Sync last byte", actionPerformed=self.check_sync_last_byte)
            self.option_sync_last_byte.setToolTipText(
                "Select whether last byte synchronisation is enabled")
            c.gridx = 2
            c.gridy = 1
            c.insets = Insets(0, 20, 0, 0)
            self._settings_pane.add(self.option_sync_last_byte, c)

            self.label_2 = JLabel("Send timeout in seconds:")
            c.gridx = 0
            c.gridy = 1
            c.insets = Insets(0, 5, 0, 0)
            self._settings_pane.add(self.label_2, c)

            self.input_send_timeout = JComboBox([
                Item(item2),
                Item(item4),
                Item(item5),
                Item(item7),
                Item(item9),
                Item(item10)
            ])
            self.input_send_timeout.setSelectedIndex(3)
            self.input_send_timeout.setToolTipText(
                "Select the wait-for-response timeout after sending the request(s)"
            )
            self.input_send_timeout.addActionListener(self.change_send_timeout)
            c.gridx = 1
            c.gridy = 1
            c.insets = Insets(0, 5, 0, 0)
            self._settings_pane.add(self.input_send_timeout, c)

            self.button_resend_batch = JButton("Resend requests")
            self.button_resend_batch.setToolTipText(
                "Resend all requests with the current configuration")
            self.button_resend_batch.setEnabled(False)
            self.button_resend_batch.addActionListener(
                MenuFactory.start_request_transmitter_button)
            c.gridx = 3
            c.gridy = 0
            c.insets = Insets(0, 20, 0, 10)
            self._settings_pane.add(self.button_resend_batch, c)

            immediate_data_ui_elements[
                "parallel_requests"] = self.input_parallel_requests
            immediate_data_ui_elements[
                "allow_redirects"] = self.option_allow_redirects
            immediate_data_ui_elements[
                "sync_last_byte"] = self.option_sync_last_byte
            immediate_data_ui_elements[
                "send_timeout"] = self.input_send_timeout
            immediate_data_ui_elements[
                "resend_batch"] = self.button_resend_batch

            c = GridBagConstraints()
            c.anchor = GridBagConstraints.WEST
            self._outer_settings_pane.add(self._settings_pane,
                                          BorderLayout.WEST)
            self._main_splitpane.setTopComponent(self._outer_settings_pane)

            self._results_splitpane = JSplitPane(JSplitPane.HORIZONTAL_SPLIT)
            self._main_splitpane.setBottomComponent(self._results_splitpane)

            # table of log entries
            self.tabs_right = JTabbedPane()
            global _textEditors, DEFAULT_RESULTS
            for i in range(3):
                _textEditors.append(Cb.callbacks.createTextEditor())
                _textEditors[-1].setText(str.encode("\n" + DEFAULT_RESULTS))

            self.tabs_right.add("Summary", _textEditors[0].getComponent())
            self.tabs_right.add("Full result", _textEditors[1].getComponent())
            self.tabs_right.add("Config", _textEditors[2].getComponent())
            self._results_splitpane.setRightComponent(self.tabs_right)

            # tabs with request/response viewers
            global _requestViewers, _requestPane
            _requestPane = JTabbedPane()
            _requestViewers.append(
                Cb.callbacks.createMessageEditor(None, False))
            _requestPane.addTab("Request", _requestViewers[-1].getComponent())
            self._results_splitpane.setLeftComponent(_requestPane)

            # customize our UI components
            Cb.callbacks.customizeUiComponent(self._settings_pane)
            Cb.callbacks.customizeUiComponent(self.tabs_right)
            Cb.callbacks.customizeUiComponent(_requestPane)

            # add the custom tab to Burp's UI
            Cb.callbacks.addSuiteTab(self)

        except RuntimeException as e:
            callbacks.printError(traceback.format_exc())
            e = PyException(e)
            print("10")
            print(str(self))
            print("{}\t{}\n{}\n".format(e.type, e.value, e.traceback))
        Cb.callbacks.registerContextMenuFactory(MenuFactory())
        callbacks.registerExtensionStateListener(self)

        self.start_alive_checker()

        Cb.callbacks.printOutput('%s v%s extension loaded\n' %
                                 (self.ext_name, self.ext_version))

    def change_parallel_requests(self, event):
        global immediate_data
        try:
            num_parallel = MenuFactory.item_selected(event)
            if num_parallel != immediate_data['settings'][0]:
                self.update_setting(0, num_parallel,
                                    "number of parallel requests")
        except Exception as e:
            print(e)

    def change_send_timeout(self, event):
        global immediate_data
        try:
            send_timeout = MenuFactory.item_selected(event)
            if send_timeout != immediate_data['settings'][4]:
                self.update_setting(4, send_timeout, "send timeout")
        except Exception as e:
            print(e)

    def check_allow_redirects(self, event):
        global immediate_data
        is_selected = MenuFactory.button_selected(event)
        if is_selected != immediate_data['settings'][2]:
            self.update_setting(2, is_selected, "allow redirects")

    def check_sync_last_byte(self, event):
        global immediate_data
        is_selected = MenuFactory.button_selected(event)
        if is_selected != immediate_data['settings'][3]:
            self.update_setting(3, is_selected, "allow redirects")

    def resend_batches(self, event):
        global _storedRequests
        if _storedRequests is not None:
            self.sen

    # helper method for two methods above
    def update_setting(self, index, new_value, text):
        global immediate_data
        success = True
        print("> Updating {}..".format(text))
        old_value = immediate_data['settings'][index]
        immediate_data['settings'][index] = new_value
        if MenuFactory.set_immediate_mode_settings(
            {'settings': immediate_data['settings']}):
            print("> Success!")
        else:
            print("> Failed!")
            immediate_data['settings'][index] = old_value
            success = False
        return success

    # for ITab
    def getTabCaption(self):
        return "CompuRacer"

    # for ITab
    def getUiComponent(self):
        return self._main_splitpane

    # def getHttpService(self):
    #     global _storedRequest
    #     return _storedRequest.getHttpService()
    #
    # def getRequest(self):
    #     global _storedRequest
    #     return _storedRequest.getRequest()
    #
    # def getResponse(self):
    #     global _storedRequest
    #     return _storedRequest.getResponse()

    def start_alive_checker(self):
        self.t = threading.Thread(name='Alive checker',
                                  target=self.alive_checker)
        self.t.start()

    def closest_match(self, number, list_of_numbers):
        return min(list(zip(list_of_numbers, range(len(list_of_numbers)))),
                   key=lambda item: (abs(item[0] - number), item[1]))

    def alive_checker(self):
        global compuRacer_ip, compuRacer_port, alive_check_path, racer_alive, immediate_mode, compuracer_communication_lock
        unloaded = False
        old_alive = racer_alive
        parallel_req_options = [2, 3, 4, 5, 10, 15, 20, 25, 50, 100]
        send_time_options = [3, 5, 10, 20, 50, 100]
        while not unloaded:
            try:
                with compuracer_communication_lock:
                    response = requests.get("http://{}:{}/{}".format(
                        compuRacer_ip, compuRacer_port, alive_check_path),
                                            timeout=2)
                    racer_alive = response and response.status_code and response.status_code == 200
                    success, mode, settings = MenuFactory.get_immediate_mode_settings(
                    )
                    if success:
                        immediate_data['mode'] = mode
                        immediate_data['settings'] = settings

                        # update UI button states
                        immediate_data_ui_elements[
                            "parallel_requests"].setSelectedIndex(
                                self.closest_match(
                                    immediate_data['settings'][0],
                                    parallel_req_options)[1])
                        immediate_data_ui_elements[
                            "allow_redirects"].setSelected(
                                bool(immediate_data['settings'][2]))
                        immediate_data_ui_elements[
                            "sync_last_byte"].setSelected(
                                bool(immediate_data['settings'][3]))
                        immediate_data_ui_elements[
                            "send_timeout"].setSelectedIndex(
                                self.closest_match(
                                    immediate_data['settings'][4],
                                    send_time_options)[1])

            except Exception as e:
                # it surely did not work
                racer_alive = False
                print(e)
            if racer_alive and not old_alive:
                print("> Racer is now alive!")
                MenuFactory.set_state_of_all_buttons(True)
                old_alive = True
            elif not racer_alive and old_alive:
                print("> Racer became dead!")
                MenuFactory.set_state_of_all_buttons(False)
                old_alive = False
            time.sleep(5)
            if not self.loaded:
                unloaded = True

    def extensionUnloaded(self):
        print("\n> Unloading..")
        self.loaded = False
        self.t.join()
        print("> Done.")
コード例 #9
0
class BurpExtender(IBurpExtender, ITab):
    def registerExtenderCallbacks(self, callbacks):
        print "Loading..."

        self._callbacks = callbacks
        self._callbacks.setExtensionName('Burp SPA Explorer')
        # self._callbacks.registerScannerCheck(self)
        # self._callbacks.registerExtensionStateListener(self)
        self._helpers = callbacks.getHelpers()

        self.crawlingEvent = Event()
        self.crawlerThread = None

        # main split pane
        self._splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT)
        self._splitpane.setBorder(EmptyBorder(20, 20, 20, 20))

        # sub split pane (top)
        self._topPanel = JPanel(BorderLayout(10, 10))
        self._topPanel.setBorder(EmptyBorder(0, 0, 10, 0))

        # Setup Panel :    [Target: ] [______________________] [START BUTTON]
        self.setupPanel = JPanel(FlowLayout(FlowLayout.LEADING, 10, 10))

        self.setupPanel.add(JLabel("Target:", SwingConstants.LEFT),
                            BorderLayout.LINE_START)

        self.hostField = JTextField('', 50)
        self.setupPanel.add(self.hostField)

        self.toggleButton = JButton('Start crawling',
                                    actionPerformed=self.toggleCrawl)
        self.setupPanel.add(self.toggleButton)

        self._topPanel.add(self.setupPanel, BorderLayout.PAGE_START)

        # Options Panel :    [Buttons]  [          RegEx           ]
        self.optionsPanel = JPanel()
        self.optionsPanel.setLayout(
            BoxLayout(self.optionsPanel, BoxLayout.LINE_AXIS))

        # Button options panel :    [Add][Edit][Up][Down][Remove]

        self.buttonOptionsPanel = JPanel()
        self.buttonOptionsPanel.setLayout(
            BoxLayout(self.buttonOptionsPanel, BoxLayout.PAGE_AXIS))

        self.addRegexButton = JButton('Add', actionPerformed=self.addRegex)
        self.buttonOptionsPanel.add(self.addRegexButton)

        self.editRegexButton = JButton('Edit', actionPerformed=self.editRegex)
        self.buttonOptionsPanel.add(self.editRegexButton)

        self.moveRegexUpButton = JButton('Move up',
                                         actionPerformed=self.moveRegexUp)
        self.buttonOptionsPanel.add(self.moveRegexUpButton)

        self.moveRegexDownButton = JButton('Move down',
                                           actionPerformed=self.moveRegexDown)
        self.buttonOptionsPanel.add(self.moveRegexDownButton)

        self.removeRegexButton = JButton('Remove',
                                         actionPerformed=self.removeRegex)
        self.buttonOptionsPanel.add(self.removeRegexButton)

        self.buttonOptionsPanel.add(Box.createVerticalGlue())

        self.optionsPanel.add(self.buttonOptionsPanel)

        self.optionsPanel.add(Box.createHorizontalStrut(20))

        self.regexTableModel = RegexTableModel([x for x in regex])
        self.regexTable = Table(self.regexTableModel)
        self.regexScrollPane = JScrollPane(self.regexTable)

        self.optionsPanel.add(self.regexScrollPane)

        self._topPanel.add(self.optionsPanel, BorderLayout.CENTER)
        self._splitpane.setTopComponent(self._topPanel)

        # Bottom Panel
        self._bottomPanel = JPanel(BorderLayout(10, 10))
        #self._bottomPanel.setLayout(BoxLayout(self._bottomPanel,BoxLayout.PAGE_AXIS))

        # Status bar
        self.crawlStatusPanel = JPanel(FlowLayout(FlowLayout.LEADING, 10, 10))

        self.crawlStatusPanel.add(JLabel("Status: ", SwingConstants.LEFT))

        self.crawlStatusLabel = JLabel("Ready to crawl", SwingConstants.LEFT)
        self.crawlStatusPanel.add(self.crawlStatusLabel)

        # Result Table
        self.resultTableModel = Result([])
        self.resultTable = Table(self.resultTableModel)
        self.resultTable.setAutoCreateRowSorter(True)
        self.resultScrollPane = JScrollPane(self.resultTable)

        # Result Table popup menu
        def selectWhenRightClickEvent(event):
            def select(e):
                rowAtPoint = self.resultTable.rowAtPoint(
                    SwingUtilities.convertPoint(self.resultTablePopupMenu,
                                                Point(0, 0), self.resultTable))
                if rowAtPoint > -1:
                    self.resultTable.setRowSelectionInterval(
                        rowAtPoint, rowAtPoint)

            SwingUtilities.invokeLater(CrawlerRunnable(select, (event, )))

        self.resultTablePopupMenu = JPopupMenu(
            popupMenuWillBecomeVisible=selectWhenRightClickEvent)
        self.resultTablePopupMenu.add(
            JMenuItem("Send to scanner", actionPerformed=self.sendToScanner))
        self.resultTablePopupMenu.add(
            JMenuItem("Send to repeater", actionPerformed=self.sendToRepeater))
        self.resultTablePopupMenu.add(
            JMenuItem("Send to intruder", actionPerformed=self.sendToIntruder))
        self.resultTablePopupMenu.add(
            JMenuItem("Send to spider", actionPerformed=self.sendToSpider))

        self.resultTable.setComponentPopupMenu(self.resultTablePopupMenu)

        self._bottomPanel.add(self.resultScrollPane, BorderLayout.CENTER)
        self._bottomPanel.add(self.crawlStatusPanel, BorderLayout.SOUTH)

        self._splitpane.setBottomComponent(self._bottomPanel)
        self._splitpane.setDividerLocation(300 +
                                           self._splitpane.getInsets().left)

        callbacks.customizeUiComponent(self._splitpane)

        callbacks.addSuiteTab(self)

        explorerMenu = ExplorerMenu(self)
        callbacks.registerContextMenuFactory(explorerMenu)
        print "SPA Explorer custom menu loaded"

        #print "Loading chrome driver"
        #a = Test(os.path.dirname(os.path.realpath('selenium-client.jar')) + '/chromedriver.exe')
        #print "Chrome driver started"

        print "Burp SPA Explorer loaded"

    # Button Actions

    def getURLComponents(self, url):
        return (url.getHost(), (443 if url.getProtocol() == 'https' else 80)
                if url.getPort() == -1 else url.getPort(),
                url.getProtocol() == 'https')

    def sendToScanner(self, event):
        url = URL(
            self.resultTable.getValueAt(self.resultTable.getSelectedRow(), 1))
        urlComp = self.getURLComponents(url)
        self._callbacks.doActiveScan(urlComp[0], urlComp[1], urlComp[2],
                                     self._helpers.buildHttpRequest(url))

    def sendToRepeater(self, event):
        url = URL(
            self.resultTable.getValueAt(self.resultTable.getSelectedRow(), 1))
        urlComp = self.getURLComponents(url)
        self._callbacks.sendToRepeater(urlComp[0], urlComp[1], urlComp[2],
                                       self._helpers.buildHttpRequest(url),
                                       None)

    def sendToIntruder(self, event):
        url = URL(
            self.resultTable.getValueAt(self.resultTable.getSelectedRow(), 1))
        urlComp = self.getURLComponents(url)
        self._callbacks.sendToIntruder(urlComp[0], urlComp[1], urlComp[2],
                                       self._helpers.buildHttpRequest(url))

    def sendToSpider(self, event):
        url = URL(
            self.resultTable.getValueAt(self.resultTable.getSelectedRow(), 1))
        self._callbacks.sendToSpider(url)

    def addRegex(self, event):
        optionPane = JOptionPane()
        dialog = optionPane.createDialog(self._splitpane, "Add RegEx")

        panel = JPanel(GridLayout(0, 2))
        panel.setBorder(EmptyBorder(10, 10, 10, 10))

        nameField = JTextField('', 15)
        panel.add(JLabel("Name:", SwingConstants.LEFT))
        panel.add(nameField)

        regexField = JTextField('', 15)
        panel.add(JLabel("RegEx:", SwingConstants.LEFT))
        panel.add(regexField)

        crawlField = JCheckBox()
        panel.add(JLabel("Crawl:", SwingConstants.LEFT))
        panel.add(crawlField)

        def closeDialog(event):
            if len(nameField.text) == 0 or len(regexField.text) == 0:
                JOptionPane.showMessageDialog(self._splitpane,
                                              "Name or RegEx can't be empty",
                                              "Error",
                                              JOptionPane.ERROR_MESSAGE)
                return
            self.regexTableModel.addRow(
                [nameField.text, regexField.text,
                 crawlField.isSelected()])
            dialog.hide()

        addButton = JButton('OK', actionPerformed=closeDialog)
        panel.add(addButton)

        dialog.setSize(600, 200)
        dialog.setContentPane(panel)
        self._callbacks.customizeUiComponent(dialog)
        dialog.show()

        return True

    def editRegex(self, event):
        selectedRowIdx = self.regexTable.getSelectedRow()
        if selectedRowIdx == -1: return False
        selectedRow = self.regexTableModel.data[selectedRowIdx]

        optionPane = JOptionPane()
        dialog = optionPane.createDialog(self._splitpane, "Edit RegEx")

        panel = JPanel(GridLayout(0, 2))
        panel.setBorder(EmptyBorder(10, 10, 10, 10))

        nameField = JTextField('', 15)
        nameField.text = selectedRow[0]
        panel.add(JLabel("Name:", SwingConstants.LEFT))
        panel.add(nameField)

        regexField = JTextField('', 15)
        regexField.text = selectedRow[1]
        panel.add(JLabel("RegEx:", SwingConstants.LEFT))
        panel.add(regexField)

        crawlField = JCheckBox()
        crawlField.setSelected(selectedRow[2])
        panel.add(JLabel("Crawl:", SwingConstants.LEFT))
        panel.add(crawlField)

        def closeDialog(event):
            if len(nameField.text) == 0 or len(regexField.text) == 0:
                JOptionPane.showMessageDialog(self._splitpane,
                                              "Name or RegEx can't be empty",
                                              "Error",
                                              JOptionPane.ERROR_MESSAGE)
                return
            self.regexTableModel.editRow(
                selectedRowIdx,
                [nameField.text, regexField.text,
                 crawlField.isSelected()])
            dialog.hide()

        editButton = JButton('OK', actionPerformed=closeDialog)
        panel.add(editButton)

        dialog.setSize(600, 200)
        dialog.setContentPane(panel)
        self._callbacks.customizeUiComponent(dialog)
        dialog.show()
        return True

    def moveRegexDown(self, event):
        idxs = self.regexTable.getSelectedRows()
        if self.regexTableModel.getRowCount() - 1 in idxs: return False

        self.regexTable.clearSelection()
        for i in sorted(idxs)[::-1]:
            self.regexTableModel.moveDown(i)
            self.regexTable.addRowSelectionInterval(i + 1, i + 1)
        return True

    def moveRegexUp(self, event):
        idxs = self.regexTable.getSelectedRows()
        if 0 in idxs: return False

        self.regexTable.clearSelection()
        for i in sorted(idxs):
            self.regexTableModel.moveUp(i)
            self.regexTable.addRowSelectionInterval(i - 1, i - 1)
        return True

    def removeRegex(self, event):
        idx = self.regexTable.getSelectedRows()
        for i in sorted(idx)[::-1]:
            self.regexTableModel.removeRow(i)
        return True

    # Implement ITab

    def getTabCaption(self):
        return "SPA Explorer"

    def getUiComponent(self):
        return self._splitpane

    def crawl(self, event):
        print("Starting")

        host = self.hostField.text

        if host.find("://") == -1:
            host = "http://" + host

        try:
            self._callbacks.includeInScope(URL(host))
        except:
            JOptionPane.showMessageDialog(self._splitpane,
                                          "Can't add host to scope", "Error",
                                          JOptionPane.ERROR_MESSAGE)
            return

        self.resultTableModel.clearAllRow()

        self.crawlingEvent.set()
        self.crawlerThread = Thread(target=self.crawl_thread, args=(host, ))
        self.crawlerThread.start()
        print("Started")

    def stopCrawling(self, event):
        print("Clear event")
        self.crawlingEvent.clear()

        # Disable button
        if self.toggleButton.text == "Stop crawling":  # If button is still "Stop crawling" (Thread still running), disable button
            self.toggleButton.setEnabled(False)

    def toggleCrawl(self, event):
        if (self.crawlerThread == None or not self.crawlerThread.is_alive()):
            self.crawl(event)
            #self.toggleButton.setText("Start crawling")
        else:
            self.stopCrawling(event)
            #self.toggleButton.setText("Stop crawling")

    def crawl_thread(self, host):
        # print(self, host)
        print("Crawl thread started")

        SwingUtilities.invokeLater(
            CrawlerRunnable(self.toggleButton.setText, ("Stop crawling", )))
        SwingUtilities.invokeLater(
            CrawlerRunnable(self.addRegexButton.setEnabled, (False, )))
        SwingUtilities.invokeLater(
            CrawlerRunnable(self.editRegexButton.setEnabled, (False, )))
        SwingUtilities.invokeLater(
            CrawlerRunnable(self.moveRegexUpButton.setEnabled, (False, )))
        SwingUtilities.invokeLater(
            CrawlerRunnable(self.moveRegexDownButton.setEnabled, (False, )))
        SwingUtilities.invokeLater(
            CrawlerRunnable(self.removeRegexButton.setEnabled, (False, )))

        pageType = {}  # url -> type
        pageContentHash = {}  # hash -> url list

        def concatURL(baseURL, link):
            return URL(URL(baseURL), link).toString()

        def makeRequest(url):
            url = URL(url)

            if not self._callbacks.isInScope(url):
                #self.logger.addRow(url.toString()+" is out of scope")
                raise ValueError("URL is out of scope")

            prot = url.getProtocol()
            host = url.getHost()
            port = url.getPort()
            if port == -1:
                port = 80 if prot == "http" else 443

            httpService = self._helpers.buildHttpService(host, port, prot)

            reqRes = self._callbacks.makeHttpRequest(
                httpService, self._helpers.buildHttpRequest(url))
            self._callbacks.addToSiteMap(reqRes)
            resp = reqRes.getResponse()
            respInfo = self._helpers.analyzeResponse(resp)

            respBody = self._helpers.bytesToString(
                resp[respInfo.getBodyOffset():])
            return respBody

        def matchRegex(baseURL, res):
            toRet = []
            for (name, regStr, ret) in self.regexTableModel.data:
                matchObj = re.findall(regStr, res, re.M | re.I)
                for i in matchObj:
                    try:
                        if i.find('http://') == 0 or i.find('https://') == 0:
                            url = i
                        elif i[0] == '/':
                            url = host + i
                        else:
                            url = host + '/' + i

                        if url not in pageType:
                            pageType[url] = name
                            SwingUtilities.invokeLater(
                                CrawlerRunnable(self.resultTableModel.addRow,
                                                ([name, url], )))

                            if ret:
                                toRet.append(url)
                    except:
                        print("Error when trying to save result ", i,
                              sys.exc_info()[0],
                              sys.exc_info()[1])
            return toRet

        def getAllLink(url):
            toRet = []
            try:
                print("Making request", url)
                r = makeRequest(url)
                print("Done request", len(r))
                hash = hashlib.sha256(r.encode('utf-8')).hexdigest()
                #print(r.text)
                if hash in pageContentHash:
                    print("Content hash is the same as ",
                          pageContentHash[hash][0])
                    pageContentHash[hash].append(url)
                    return toRet
                else:
                    pageContentHash[hash] = [url]

                toRet += matchRegex(url, r)
            except BaseException as e:
                print("Error while making request to ", url, e)
            except:
                print("Error while making request to ", url,
                      sys.exc_info()[0],
                      sys.exc_info()[1])
            return toRet

        crawledPage = [host]
        crawledNow = 0

        SwingUtilities.invokeLater(
            CrawlerRunnable(self.resultTableModel.addRow,
                            (["TARGET", host], )))

        while crawledNow < len(crawledPage):
            if self.crawlingEvent.is_set():
                print("Crawling", crawledPage[crawledNow])
                SwingUtilities.invokeLater(
                    CrawlerRunnable(self.crawlStatusLabel.setText,
                                    ("Crawling " + crawledPage[crawledNow], )))
                for i in getAllLink(crawledPage[crawledNow]):
                    if i not in crawledPage:
                        print("ADD:", i)
                        crawledPage.append(i)
                crawledNow += 1
            else:
                print("Stop Requested")
                break

        print(crawledNow, crawledPage)
        output = []

        SwingUtilities.invokeLater(
            CrawlerRunnable(self.toggleButton.setText, ("Start crawling", )))
        SwingUtilities.invokeLater(
            CrawlerRunnable(self.toggleButton.setEnabled, (True, )))
        SwingUtilities.invokeLater(
            CrawlerRunnable(self.addRegexButton.setEnabled, (True, )))
        SwingUtilities.invokeLater(
            CrawlerRunnable(self.editRegexButton.setEnabled, (True, )))
        SwingUtilities.invokeLater(
            CrawlerRunnable(self.moveRegexUpButton.setEnabled, (True, )))
        SwingUtilities.invokeLater(
            CrawlerRunnable(self.moveRegexDownButton.setEnabled, (True, )))
        SwingUtilities.invokeLater(
            CrawlerRunnable(self.removeRegexButton.setEnabled, (True, )))

        SwingUtilities.invokeLater(
            CrawlerRunnable(self.crawlStatusLabel.setText,
                            ("Ready to crawl", )))

        self.crawlingEvent.clear()
        print("Completed")
コード例 #10
0
ファイル: UPnPHunter_Burp.py プロジェクト: t1v0/upnp-hunter
class BurpExtender(IBurpExtender, ITab, IExtensionStateListener):
    # Define the global variables for the burp plugin
    EXTENSION_NAME = "UPnP BHunter"
    ipv4_selected = True
    services_dict = {}
    ip_service_dict = {}
    STOP_THREAD = False

    #Some  SSDP m-search parameters are based upon "UPnP Device Architecture v2.0"
    SSDP_MULTICAST_IPv4 = ["239.255.255.250"]
    SSDP_MULTICAST_IPv6 = ["FF02::C", "FF05::C"]
    SSDP_MULTICAST_PORT = 1900
    ST_ALL = "ssdp:all"
    ST_ROOTDEV = "upnp:rootdevice"
    PLACEHOLDER = "FUZZ_HERE"
    SSDP_TIMEOUT = 2

    def registerExtenderCallbacks(self, callbacks):
        # Get a reference to callbacks object
        self.callbacks = callbacks
        # Get the useful extension helpers object
        self.helpers = callbacks.getHelpers()
        # Set the extension name
        self.callbacks.setExtensionName(self.EXTENSION_NAME)
        self.callbacks.registerExtensionStateListener(self)
        # Draw plugin user interface
        self.drawPluginUI()
        self.callbacks.addSuiteTab(self)
        # Plugin loading message
        print("[+] Burp plugin UPnP BHunter loaded successfully")
        return

    def drawPluginUI(self):
        # Create the plugin user interface
        self.pluginTab = JPanel()
        self.uiTitle = JLabel('UPnP BHunter Load, Aim and Fire Console')
        self.uiTitle.setFont(Font('Tahoma', Font.BOLD, 14))
        self.uiTitle.setForeground(Color(250, 100, 0))
        self.uiPanelA = JSplitPane(JSplitPane.VERTICAL_SPLIT)
        self.uiPanelA.setMaximumSize(Dimension(2500, 1000))
        self.uiPanelA.setDividerSize(2)
        self.uiPanelB = JSplitPane(JSplitPane.VERTICAL_SPLIT)
        self.uiPanelB.setDividerSize(2)
        self.uiPanelA.setBottomComponent(self.uiPanelB)
        self.uiPanelA.setBorder(BorderFactory.createLineBorder(Color.gray))

        # Create and configure labels and text fields
        self.labeltitle_step1 = JLabel("[1st STEP] Discover UPnP Locations")
        self.labeltitle_step1.setFont(Font('Tahoma', Font.BOLD, 14))
        self.labeltitle_step2 = JLabel(
            "[2nd STEP] Select a UPnP Service and Action")
        self.labeltitle_step2.setFont(Font('Tahoma', Font.BOLD, 14))
        self.labeltitle_step3 = JLabel("[3rd STEP] Time to Attack it")
        self.labeltitle_step3.setFont(Font('Tahoma', Font.BOLD, 14))
        self.labelsubtitle_step1 = JLabel(
            "Specify the IP version address in scope and start UPnP discovery")
        self.labelsubtitle_step2 = JLabel(
            "Select which of the found UPnP services will be probed")
        self.labelsubtitle_step3 = JLabel(
            "Review and modify the request, then send it to one of the attack tools"
        )
        self.label_step1 = JLabel("Target IP")
        self.label_step2 = JLabel("Found UPnp Services")
        self.labelstatus = JLabel("             Status")
        self.labelempty_step1 = JLabel("                ")
        self.labelempty_step2 = JLabel("  ")
        self.labelupnp = JLabel("UPnP list")
        self.labelip = JLabel("IP list")
        self.labelactions = JLabel("Actions")
        self.labelNoneServiceFound = JLabel("  ")
        self.labelNoneServiceFound.setFont(Font('Tahoma', Font.BOLD, 12))
        self.labelNoneServiceFound.setForeground(Color.red)

        # Create combobox for IP version selection
        self.ip_versions = ["IPv4", "IPv6"]
        self.combo_ipversion = JComboBox(self.ip_versions)
        self.combo_ipversion.setSelectedIndex(0)
        self.combo_ipversion.setEnabled(True)

        # Create and configure progress bar
        self.progressbar = JProgressBar(0, 100)
        self.progressbar.setString("Ready")
        self.progressbar.setStringPainted(True)

        # Create and configure buttons
        self.startbutton = JButton("Start Discovery",
                                   actionPerformed=self.startHunting)
        self.clearbutton = JButton("Clear All", actionPerformed=self.clearAll)
        self.intruderbutton = JButton("Send to Intruder",
                                      actionPerformed=self.sendToIntruder)
        self.repeaterbutton = JButton("Send to Repeater",
                                      actionPerformed=self.sendToRepeater)
        #self.WANrepeaterbutton = JButton("to Repeater", actionPerformed=self.sendWANUPnPToRepeater)
        self.textarea_request = JTextArea(18, 90)
        self.intruderbutton.setEnabled(False)
        self.repeaterbutton.setEnabled(False)

        # Class neeeded to handle the target combobox in second step panel
        class TargetComboboxListener(ActionListener):
            def __init__(self, upnpcombo_targets, upnpcombo_services,
                         ip_service_dict):
                self.upnpcombo_targets = upnpcombo_targets
                self.upnpcombo_services = upnpcombo_services
                self.ip_service_dict = ip_service_dict

            def actionPerformed(self, event):
                try:
                    # Update the location url combobox depending on the IP combobox
                    selected_target = self.upnpcombo_targets.getSelectedItem()
                    if self.ip_service_dict and selected_target:
                        self.upnpcombo_services.removeAllItems()
                        for service_url in self.ip_service_dict[
                                selected_target]:
                            self.upnpcombo_services.addItem(service_url)
                        self.upnpcombo_services.setSelectedIndex(0)
                except BaseException as e:
                    print("[!] Exception selecting service: \"%s\" ") % e

        # Class neeeded to handle the service combobox in second step panel
        class ServiceComboboxListener(ActionListener):
            def __init__(self, upnpcombo_services, upnpcombo_actions,
                         services_dict):
                self.upnpcombo_services = upnpcombo_services
                self.upnpcombo_actions = upnpcombo_actions
                self.services = services_dict

            def actionPerformed(self, event):
                try:
                    # Update the location url combobox depending on the IP combobox
                    selected_service = self.upnpcombo_services.getSelectedItem(
                    )
                    if self.services and selected_service:
                        self.upnpcombo_actions.removeAllItems()
                        actions = self.services[selected_service]
                        for action in actions:
                            self.upnpcombo_actions.addItem(action)
                        self.upnpcombo_actions.setSelectedIndex(0)
                except BaseException as e:
                    print("[!] Exception selecting service: \"%s\" ") % e

        # Class neeeded to handle the action combobox in second step panel
        class ActionComboboxListener(ActionListener):
            def __init__(self, upnpcombo_services, upnpcombo_actions,
                         textarea_request, services_dict):
                self.upnpcombo_services = upnpcombo_services
                self.upnpcombo_actions = upnpcombo_actions
                self.textarea_request = textarea_request
                self.services = services_dict

            def actionPerformed(self, event):
                try:
                    # Update the location url combobox depending on the IP combobox
                    selected_action = self.upnpcombo_actions.getSelectedItem()
                    selected_service = self.upnpcombo_services.getSelectedItem(
                    )
                    if self.services and selected_action:
                        self.textarea_request.setText(
                            self.services[selected_service][selected_action])
                except BaseException as e:
                    print("[!] Exception selecting action: \"%s\" ") % e

        self.upnpactions = ["       "]
        self.upnpcombo_actions = JComboBox(self.upnpactions)
        self.upnpcombo_actions.setSelectedIndex(0)
        self.upnpcombo_actions.setEnabled(False)

        # Create the combo box, select item at index 0 (first item in list)
        self.upnpservices = ["       "]
        self.upnpcombo_services = JComboBox(self.upnpservices)
        self.upnpcombo_services.setSelectedIndex(0)
        self.upnpcombo_services.setEnabled(False)

        # Create the combo box, select item at index 0 (first item in list)
        self.upnptargets = ["       "]
        self.upnpcombo_targets = JComboBox(self.upnptargets)
        self.upnpcombo_targets.setSelectedIndex(0)
        self.upnpcombo_targets.setEnabled(False)

        # Set the action listeners for all the comboboxes
        self.upnpcombo_targets.addActionListener(
            TargetComboboxListener(self.upnpcombo_targets,
                                   self.upnpcombo_services,
                                   self.ip_service_dict))
        self.upnpcombo_services.addActionListener(
            ServiceComboboxListener(self.upnpcombo_services,
                                    self.upnpcombo_actions,
                                    self.services_dict))
        self.upnpcombo_actions.addActionListener(
            ActionComboboxListener(self.upnpcombo_services,
                                   self.upnpcombo_actions,
                                   self.textarea_request, self.services_dict))

        # Configuring first step panel
        self.panel_step1 = JPanel()
        self.panel_step1.setPreferredSize(Dimension(2250, 100))
        self.panel_step1.setBorder(EmptyBorder(10, 10, 10, 10))
        self.panel_step1.setLayout(BorderLayout(15, 15))
        self.titlepanel_step1 = JPanel()
        self.titlepanel_step1.setLayout(BorderLayout())
        self.titlepanel_step1.add(self.labeltitle_step1, BorderLayout.NORTH)
        self.titlepanel_step1.add(self.labelsubtitle_step1)
        self.targetpanel_step1 = JPanel()
        self.targetpanel_step1.add(self.label_step1)
        self.targetpanel_step1.add(self.combo_ipversion)
        self.targetpanel_step1.add(self.startbutton)
        self.targetpanel_step1.add(self.clearbutton)
        self.targetpanel_step1.add(self.labelstatus)
        self.targetpanel_step1.add(self.progressbar)
        self.emptypanel_step1 = JPanel()
        self.emptypanel_step1.setLayout(BorderLayout())
        self.emptypanel_step1.add(self.labelempty_step1, BorderLayout.WEST)

        # Assembling first step panel components
        self.panel_step1.add(self.titlepanel_step1, BorderLayout.NORTH)
        self.panel_step1.add(self.targetpanel_step1, BorderLayout.WEST)
        self.panel_step1.add(self.emptypanel_step1, BorderLayout.SOUTH)
        self.uiPanelA.setTopComponent(self.panel_step1)

        # Configure second step panel
        self.panel_step2 = JPanel()
        self.panel_step2.setPreferredSize(Dimension(2250, 100))
        self.panel_step2.setBorder(EmptyBorder(10, 10, 10, 10))
        self.panel_step2.setLayout(BorderLayout(15, 15))
        self.titlepanel_step2 = JPanel()
        self.titlepanel_step2.setLayout(BorderLayout())
        self.titlepanel_step2.add(self.labeltitle_step2, BorderLayout.NORTH)
        self.titlepanel_step2.add(self.labelsubtitle_step2)
        self.selectpanel_step2 = JPanel()
        self.selectpanel_step2.add(self.labelip)
        self.selectpanel_step2.add(self.upnpcombo_targets)
        self.selectpanel_step2.add(self.labelupnp)
        self.selectpanel_step2.add(self.upnpcombo_services)
        self.selectpanel_step2.add(self.labelactions)
        self.selectpanel_step2.add(self.upnpcombo_actions)
        self.emptypanel_step2 = JPanel()
        self.emptypanel_step2.setLayout(BorderLayout())
        self.emptypanel_step2.add(self.labelempty_step2, BorderLayout.WEST)
        self.emptypanel_step2.add(self.labelNoneServiceFound)

        # Assembling second step panel components
        self.panel_step2.add(self.titlepanel_step2, BorderLayout.NORTH)
        self.panel_step2.add(self.selectpanel_step2, BorderLayout.WEST)
        self.panel_step2.add(self.emptypanel_step2, BorderLayout.SOUTH)
        self.uiPanelB.setTopComponent(self.panel_step2)

        # Configuring third step panel
        self.panel_step3 = JPanel()
        self.panel_step3.setPreferredSize(Dimension(2250, 100))
        self.panel_step3.setBorder(EmptyBorder(10, 10, 10, 10))
        self.panel_step3.setLayout(BorderLayout(15, 15))
        self.titlepanel_step3 = JPanel()
        self.titlepanel_step3.setLayout(BorderLayout())
        self.titlepanel_step3.add(self.labeltitle_step3, BorderLayout.NORTH)
        self.titlepanel_step3.add(self.labelsubtitle_step3)
        self.underpanel_step3 = JPanel()
        self.underpanel_step3.setLayout(BorderLayout())
        self.underpanel_step3.add((JScrollPane(self.textarea_request)),
                                  BorderLayout.NORTH)
        self.actionpanel_step3 = JPanel()
        self.actionpanel_step3.add(self.intruderbutton)
        self.actionpanel_step3.add(self.repeaterbutton)
        self.extrapanel_step3 = JPanel()
        self.extrapanel_step3.setLayout(BorderLayout())
        self.extrapanel_step3.add(self.actionpanel_step3, BorderLayout.WEST)

        # Assembling thirdd step panel components
        self.panel_step3.add(self.titlepanel_step3, BorderLayout.NORTH)
        self.panel_step3.add(self.underpanel_step3, BorderLayout.WEST)
        self.panel_step3.add(self.extrapanel_step3, BorderLayout.SOUTH)
        self.uiPanelB.setBottomComponent(self.panel_step3)

        # Assembling the group of all panels
        layout = GroupLayout(self.pluginTab)
        self.pluginTab.setLayout(layout)
        layout.setHorizontalGroup(
            layout.createParallelGroup(GroupLayout.Alignment.LEADING).addGroup(
                layout.createSequentialGroup().addGap(10, 10, 10).addGroup(
                    layout.createParallelGroup(
                        GroupLayout.Alignment.LEADING).addComponent(
                            self.uiTitle).addGap(15, 15, 15).addComponent(
                                self.uiPanelA)).addContainerGap(
                                    26, Short.MAX_VALUE)))
        layout.setVerticalGroup(
            layout.createParallelGroup(GroupLayout.Alignment.LEADING).addGroup(
                layout.createSequentialGroup().addGap(15, 15, 15).addComponent(
                    self.uiTitle).addGap(15, 15, 15).addComponent(
                        self.uiPanelA).addGap(20, 20, 20).addGap(20, 20, 20)))

    def extensionUnloaded(self):
        # Unload the plugin, and if running stop the background thread
        if self.upnpcombo_services.isEnabled():
            if self.th.isAlive():
                print("[+] Stopping thread %s") % self.th.getName()
                self.STOP_THREAD = True
                self.th.join()
            else:
                print("Thread %s already dead") % self.th.getName()
        print("[+] Burp plugin UPnP BHunter successfully unloaded")
        return

    def getTabCaption(self):
        return self.EXTENSION_NAME

    def getUiComponent(self):
        return self.pluginTab

    def clearAll(self, e=None):
        # Reset all data of the plugin
        self.services_dict.clear()
        self.progressbar.setString("Ready")
        self.progressbar.setValue(0)
        self.upnpcombo_targets.removeAllItems()
        self.upnpcombo_targets.setEnabled(False)
        self.upnpcombo_services.removeAllItems()
        self.upnpcombo_services.setEnabled(False)
        self.upnpcombo_actions.removeAllItems()
        self.upnpcombo_actions.setEnabled(False)
        self.intruderbutton.setEnabled(False)
        self.repeaterbutton.setEnabled(False)
        self.labelNoneServiceFound.setText(" ")
        self.textarea_request.setText(" ")
        print("[+] Clearing all data")
        return

    def startHunting(self, e=None):
        # Starting the UPnP hunt
        def startHunting_run():

            # Initialize the internal parameters every time the start-discovery button is clicked
            self.services_dict.clear()
            found_loc = []
            discovery_files = []
            self.labelNoneServiceFound.setText(" ")
            self.intruderbutton.setEnabled(False)
            self.repeaterbutton.setEnabled(False)

            # Then determine if targerting IPv4 or IPv6 adresses
            if self.combo_ipversion.getSelectedItem() == "IPv4":
                self.ipv4_selected = True
                print("[+] Selected IPv4 address scope")
            else:
                self.ipv4_selected = False
                print("[+] Selected IPv6 address scope")

            # And here finally the hunt could start
            self.progressbar.setString("Running...")
            self.progressbar.setValue(20)
            found_loc = self.discoverUpnpLocations()
            self.progressbar.setValue(40)
            discovery_files = self.downloadXMLfiles(found_loc)
            self.progressbar.setValue(60)
            self.buildSOAPs(discovery_files)
            self.progressbar.setValue(80)
            self.progressbar.setString("Done")
            self.progressbar.setValue(100)
            self.updateComboboxList(self.services_dict)

            # Update the comboboxes list with the discovered UPnPs
            if (self.services_dict):
                self.upnpcombo_targets.setEnabled(True)
                self.upnpcombo_services.setEnabled(True)
                self.upnpcombo_actions.setEnabled(True)
                self.intruderbutton.setEnabled(True)
                self.repeaterbutton.setEnabled(True)

            if self.STOP_THREAD:
                return

        # Start a background thread to run the above nested function in order to prevent the blocking of plugin UI
        self.th = threading.Thread(target=startHunting_run)
        #self.th.daemon = True    # This does not seem to be useful
        self.th.setName("th-BHunter")
        self.th.start()

    def ssdpReqBuilder(self, ssdp_timeout, st_type, ssdp_ip, ssdp_port):
        # Builder of the two ssdp msearch request types
        msearch_req = "M-SEARCH * HTTP/1.1\r\n" \
        "HOST: {0}:{1}\r\n" \
        "MAN: \"ssdp:discover\"\r\n" \
        "MX: {2}\r\n" \
        "ST: {3}\r\n" \
        "\r\n" \
        .format(ssdp_ip, ssdp_port, ssdp_timeout, st_type)
        return msearch_req

    def sendMsearch(self, ssdp_req, ssdp_ip, ssdp_port):
        # Send the ssdp request and retrieve response
        buf_resp = set()
        if self.ipv4_selected:
            print("[+] Creating IPv4 SSDP multicast request")
            sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
        else:
            print("[+] Creating IPv6 SSDP multicast request")
            sock = socket.socket(socket.AF_INET6, socket.SOCK_DGRAM)
        sock.setblocking(0)
        # Sending ssdp requests
        while len(ssdp_req):
            # Blocking socket client until the request is completely sent
            try:
                sent = sock.sendto(ssdp_req.encode("ASCII"),
                                   (ssdp_ip, ssdp_port))
                ssdp_req = ssdp_req[sent:]
            except socket.error, exc:
                if exc.errno != errno.EAGAIN:
                    print("[E] Got error %s with socket when sending") % exc
                    sock.close()
                    raise exc
                print("[!] Blocking socket until ", len(ssdp_req), " is sent.")
                select.select([], [sock], [])
                continue
        # Retrieving ssdp responses
        num_resp = 0
        while sock:
            # Blocking socket until there are ssdp responses to be read or timeout is reached
            readable, __, __ = select.select([sock], [], [], self.SSDP_TIMEOUT)
            if not readable:
                # Timeout reached without receiving any ssdp response
                if num_resp == 0:
                    print(
                        "[!] Got timeout without receiving any ssdp response.")
                break
            else:
                num_resp = num_resp + 1
                # Almost an ssdp response was received
                if readable[0]:
                    try:
                        data = sock.recv(1024)
                        if data:
                            buf_resp.add(data.decode('ASCII'))
                    except socket.error, exc:
                        print("[E] Got error %s with socket when receiving"
                              ) % exc
                        sock.close()
                        raise exc
コード例 #11
0
class BurpExtender(IBurpExtender, ITab):
    def registerExtenderCallbacks(self, callbacks):
        print "Loading..."

        self._callbacks = callbacks
        self._callbacks.setExtensionName('Burp SSL Scanner')
        # self._callbacks.registerScannerCheck(self)
        # self._callbacks.registerExtensionStateListener(self)
        self._helpers = callbacks.getHelpers()

        # initialize the main scanning event and thread
        self.scanningEvent = Event()
        self.scannerThread = None
        self.targetURL = None

        # main split pane
        self._splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT)
        self._splitpane.setBorder(EmptyBorder(20, 20, 20, 20))
        
        # sub split pane (top)
        self._topPanel = JPanel(BorderLayout(10, 10))
        self._topPanel.setBorder(EmptyBorder(0, 0, 10, 0))

        # Setup Panel :    [Target: ] [______________________] [START BUTTON]
        self.setupPanel = JPanel(FlowLayout(FlowLayout.LEADING, 10, 10))

        self.setupPanel.add(
            JLabel("Target:", SwingConstants.LEFT), BorderLayout.LINE_START)

        self.hostField = JTextField('', 50)
        self.setupPanel.add(self.hostField)

        self.toggleButton = JButton(
            'Start scanning', actionPerformed=self.startScan)
        self.setupPanel.add(self.toggleButton)

        if 'Professional' in callbacks.getBurpVersion()[0] :
            self.addToSitemapCheckbox = JCheckBox('Add to sitemap', True)
        else :
            self.addToSitemapCheckbox = JCheckBox('Add to sitemap (requires Professional version)', False)
            self.addToSitemapCheckbox.setEnabled(False)
        self.setupPanel.add(self.addToSitemapCheckbox)

        self.scanSiteMapHostCheckbox = JCheckBox('Scan sitemap hosts', True)
        self.setupPanel.add(self.scanSiteMapHostCheckbox)

        self._topPanel.add(self.setupPanel, BorderLayout.PAGE_START)
        
        # Status bar
        self.scanStatusPanel = JPanel(FlowLayout(FlowLayout.LEADING, 10, 10))

        self.scanStatusPanel.add(JLabel("Status: ", SwingConstants.LEFT))

        self.scanStatusLabel = JLabel("Ready to scan", SwingConstants.LEFT)
        self.scanStatusPanel.add(self.scanStatusLabel)

        self._topPanel.add(self.scanStatusPanel, BorderLayout.LINE_START)

        self._splitpane.setTopComponent(self._topPanel)

        # bottom panel 
        self._bottomPanel = JPanel(BorderLayout(10, 10))
        self._bottomPanel.setBorder(EmptyBorder(10, 0, 0, 0))

        self.initialText = ('<h1 style="color: red;">Burp SSL Scanner<br />'
                            'Please note that TLS1.3 is still not supported by this extension.</h1>')
        self.currentText = self.initialText

        self.textPane = JTextPane()
        self.textScrollPane = JScrollPane(self.textPane)
        self.textPane.setContentType("text/html")
        self.textPane.setText(self.currentText)
        self.textPane.setEditable(False)

        self._bottomPanel.add(self.textScrollPane, BorderLayout.CENTER)

        self.savePanel = JPanel(FlowLayout(FlowLayout.LEADING, 10, 10))
        self.saveButton = JButton('Save to file', actionPerformed=self.saveToFile)
        self.saveButton.setEnabled(False)
        self.savePanel.add(self.saveButton)

        self.clearScannedHostButton = JButton('Clear scanned host', actionPerformed=self.clearScannedHost)
        self.savePanel.add(self.clearScannedHostButton)
        self.savePanel.add(JLabel("Clear hosts that were scanned by active scan to enable rescanning", SwingConstants.LEFT))

        self._bottomPanel.add(self.savePanel, BorderLayout.PAGE_END)

        self._splitpane.setBottomComponent(self._bottomPanel)

        callbacks.customizeUiComponent(self._splitpane)

        callbacks.addSuiteTab(self)
        
        print "SSL Scanner tab loaded"


        self.scannerMenu = ScannerMenu(self)
        callbacks.registerContextMenuFactory(self.scannerMenu)
        print "SSL Scanner custom menu loaded"


        self.scannerCheck = ScannerCheck(self, self.scanSiteMapHostCheckbox.isSelected)
        callbacks.registerScannerCheck(self.scannerCheck)
        print "SSL Scanner check registered"

        projectConfig = json.loads(self._callbacks.saveConfigAsJson())
        scanAccuracy = projectConfig['scanner']['active_scanning_optimization']['scan_accuracy']
        scanSpeed = projectConfig['scanner']['active_scanning_optimization']['scan_speed']

        print(scanAccuracy, scanSpeed)

        self.scannedHost = []

        print 'SSL Scanner loaded'
        
    def startScan(self, ev) :

        host = self.hostField.text
        self.scanningEvent.set()
        if(len(host) == 0):
            return
        if host.find("://") == -1:
            host = "https://" + host 
        try:
            self.targetURL = URL(host)
            if(self.targetURL.getPort() == -1):
                self.targetURL = URL("https", self.targetURL.getHost(), 443, "/")
            self.hostField.setEnabled(False)
            self.toggleButton.setEnabled(False)
            self.saveButton.setEnabled(False)
            self.addToSitemapCheckbox.setEnabled(False)
            self.currentText = self.initialText
            self.textPane.setText(self.currentText)
            self.updateText("<h2>Scanning %s:%d</h2>" % (self.targetURL.getHost(), self.targetURL.getPort()))
            print("Scanning %s:%d" % (self.targetURL.getHost(), self.targetURL.getPort()))
            self.scannerThread = Thread(target=self.scan, args=(self.targetURL, ))
            self.scannerThread.start()
        except BaseException as e:
            self.saveButton.setEnabled(False)
            print(e)
            return

    def scan(self, url, usingBurpScanner=False):

        def setScanStatusLabel(text) :
            if not usingBurpScanner :
                SwingUtilities.invokeLater(
                    ScannerRunnable(self.scanStatusLabel.setText, 
                                    (text,)))
                                
        def updateResultText(text) :
            if not usingBurpScanner :
                SwingUtilities.invokeLater(
                    ScannerRunnable(self.updateText, (text, )))

        if usingBurpScanner :
            res = result.Result(url, self._callbacks, self._helpers, False)
        else :
            res = result.Result(url, self._callbacks, self._helpers, self.addToSitemapCheckbox.isSelected())

        host, port = url.getHost(), url.getPort()

        ### Get project configuration
        projectConfig = json.loads(self._callbacks.saveConfigAsJson())
        if 'scanner' in projectConfig:
            # scanAccuracy: minimise_false_negatives, normal, minimise_false_positives
            scanAccuracy = projectConfig['scanner']['active_scanning_optimization']['scan_accuracy']
            # scanSpeed: fast, normal, thorough
            scanSpeed = projectConfig['scanner']['active_scanning_optimization']['scan_speed']
        else:
            scanAccuracy = 'normal'
            scanSpeed = 'normal'

        updateResultText('<h2>Scanning speed: %s</h2> %s' % (scanSpeed, test_details.SCANNING_SPEED_INFO[scanSpeed]))
        updateResultText('<h2>Scanning accuracy: %s</h2> %s' % (scanAccuracy, test_details.SCANNING_ACCURACY_INFO[scanAccuracy]))

        try :
            setScanStatusLabel("Checking for supported SSL/TLS versions")
            con = connection_test.ConnectionTest(res, host, port, scanSpeed, scanAccuracy)
            con.start()
            conResultText = '<hr /><br /><h3>' + res.printResult('connectable') + '</h3>' + \
                '<ul><li>' + res.printResult('offer_ssl2') + '</li>' + \
                '<li>' + res.printResult('offer_ssl3') + '</li>' + \
                '<li>' + res.printResult('offer_tls10') + '</li>' + \
                '<li>' + res.printResult('offer_tls11') + '</li>' + \
                '<li>' + res.printResult('offer_tls12') + '</li></ul>'
            updateResultText(conResultText)

            
            if not res.getResult('connectable') :
                updateResultText("<h2>Scan terminated (Connection failed)</h2>")
                raise BaseException('Connection failed')

            setScanStatusLabel("Checking for supported cipher suites (This can take a long time)")
            supportedCipher = supportedCipher_test.SupportedCipherTest(res, host, port, scanSpeed, scanAccuracy)
            supportedCipher.start()

            
            setScanStatusLabel("Checking for Cipherlist")
            cipher = cipher_test.CipherTest(res, host, port, scanSpeed, scanAccuracy)
            cipher.start()
            cipherResultText = '<h3>Available ciphers:</h3>' + \
                '<ul><li>' + res.printResult('cipher_NULL') + '</li>' + \
                '<li>' + res.printResult('cipher_ANON') + '</li>' + \
                '<li>' + res.printResult('cipher_EXP') + '</li>' + \
                '<li>' + res.printResult('cipher_LOW') + '</li>' + \
                '<li>' + res.printResult('cipher_WEAK') + '</li>' + \
                '<li>' + res.printResult('cipher_3DES') + '</li>' + \
                '<li>' + res.printResult('cipher_HIGH') + '</li>' + \
                '<li>' + res.printResult('cipher_STRONG') + '</li></ul>' 
            updateResultText(cipherResultText)
            

            setScanStatusLabel("Checking for Heartbleed")
            heartbleed = heartbleed_test.HeartbleedTest(res, host, port, scanSpeed, scanAccuracy)
            heartbleed.start()
            heartbleedResultText = res.printResult('heartbleed')
            updateResultText(heartbleedResultText)
            

            setScanStatusLabel("Checking for CCS Injection")
            ccs = ccs_test.CCSTest(res, host, port, scanSpeed, scanAccuracy)
            ccs.start()
            ccsResultText = res.printResult('ccs_injection')
            updateResultText(ccsResultText)

            
            setScanStatusLabel("Checking for TLS_FALLBACK_SCSV")
            fallback = fallback_test.FallbackTest(res, host, port, scanSpeed, scanAccuracy)
            fallback.start()
            fallbackResultText = res.printResult('fallback_support')
            updateResultText(fallbackResultText)


            setScanStatusLabel("Checking for POODLE (SSLv3)")
            poodle = poodle_test.PoodleTest(res, host, port, scanSpeed, scanAccuracy)
            poodle.start()
            poodleResultText = res.printResult('poodle_ssl3')
            updateResultText(poodleResultText)
            

            setScanStatusLabel("Checking for SWEET32")
            sweet32 = sweet32_test.Sweet32Test(res, host, port, scanSpeed, scanAccuracy)
            sweet32.start()
            sweet32ResultText = res.printResult('sweet32')
            updateResultText(sweet32ResultText)
            

            setScanStatusLabel("Checking for DROWN")
            drown = drown_test.DrownTest(res, host, port, scanSpeed, scanAccuracy)
            drown.start()
            drownResultText = res.printResult('drown')
            updateResultText(drownResultText)
            

            setScanStatusLabel("Checking for FREAK")
            freak = freak_test.FreakTest(res, host, port, scanSpeed, scanAccuracy)
            freak.start()
            freakResultText = res.printResult('freak')
            updateResultText(freakResultText)
            

            setScanStatusLabel("Checking for LUCKY13")
            lucky13 = lucky13_test.Lucky13Test(res, host, port, scanSpeed, scanAccuracy)
            lucky13.start()
            lucky13ResultText = res.printResult('lucky13')
            updateResultText(lucky13ResultText)
            

            setScanStatusLabel("Checking for CRIME")
            crime = crime_test.CrimeTest(res, host, port, scanSpeed, scanAccuracy)
            crime.start()
            crimeResultText = res.printResult('crime_tls')
            updateResultText(crimeResultText)
            

            setScanStatusLabel("Checking for BREACH")
            breach = breach_test.BreachTest(res, host, port, scanSpeed, scanAccuracy)
            breach.start(self._callbacks, self._helpers)
            breachResultText = res.printResult('breach')
            updateResultText(breachResultText)


            setScanStatusLabel("Checking for BEAST")
            beast = beast_test.BeastTest(res, host, port, scanSpeed, scanAccuracy)
            beast.start()
            beastResultText = res.printResult('beast')
            updateResultText(beastResultText)


            setScanStatusLabel("Checking for LOGJAM")
            logjam = logjam_test.LogjamTest(res, host, port, scanSpeed, scanAccuracy)
            logjam.start()
            logjamResultText = res.printResult('logjam_export') + '<br />' + res.printResult('logjam_common') 
            updateResultText(logjamResultText)
            

            updateResultText('<h2>Finished scanning</h2><br /><hr /><br /><h2>Summary</h2>')

            updateResultText('<h2>Supported ciphers (by Protocol)</h2>')
            updateResultText(res.printCipherList())
            updateResultText('<h2>Supported ciphers (by Vulnerability)</h2>')
            updateResultText(res.printCipherListByVulns())

            updateResultText('<h2>Issues found</h2>')
            updateResultText(res.printAllIssue())

        except BaseException as e :
            print(e)
            setScanStatusLabel("An error occurred. Please refer to the output/errors tab for more information.")
            time.sleep(2)

        if usingBurpScanner :
            return res.getAllIssue()
        else :
            self.scanningEvent.clear()
            SwingUtilities.invokeLater(
                    ScannerRunnable(self.toggleButton.setEnabled, (True, ))
            )
            SwingUtilities.invokeLater(
                    ScannerRunnable(self.hostField.setEnabled, (True, ))
            )
            SwingUtilities.invokeLater(
                    ScannerRunnable(self.saveButton.setEnabled, (True, ))
            )
            if 'Professional' in self._callbacks.getBurpVersion()[0] :
                SwingUtilities.invokeLater(
                    ScannerRunnable(self.addToSitemapCheckbox.setEnabled, (True, ))
                )
            setScanStatusLabel("Ready to scan")
        print("Finished scanning")

    def updateText(self, stringToAppend):
        self.currentText += ('<br />' + stringToAppend)
        self.textPane.setText(self.currentText)

    def saveToFile(self, event):
        fileChooser = JFileChooser()
        if not (self.targetURL is None):
            fileChooser.setSelectedFile(File("Burp_SSL_Scanner_Result_%s.html" \
                % (self.targetURL.getHost())))
        else:
            fileChooser.setSelectedFile(File("Burp_SSL_Scanner_Result.html"))
        if (fileChooser.showSaveDialog(self.getUiComponent()) == JFileChooser.APPROVE_OPTION):
            fw = FileWriter(fileChooser.getSelectedFile())
            fw.write(self.textPane.getText())
            fw.flush()
            fw.close()
            print "Saved results to disk"

    def clearScannedHost(self, event) :
        self.scannedHost = []

    def addHostToScannedList(self, host, port) :
        self.scannedHost.append([host, port])

    def getTabCaption(self):
        return "SSL Scanner"

    def getUiComponent(self):
        return self._splitpane
コード例 #12
0
class BurpExtender(IBurpExtender, ITab, IMessageEditorController,
                   AbstractTableModel):
    """
		Implements IBurpExtender
	"""
    def registerExtenderCallbacks(self, callbacks):

        # Save callbacks and helpers for later use
        self._callbacks = callbacks
        self._helpers = callbacks.getHelpers()

        # Set extension name
        self._callbacks.setExtensionName("Burp XML Export Viewer")

        # Create the log and a lock on which to synchronize when adding log entries
        self._log = ArrayList()
        self._lock = Lock()

        # Main panel
        self._mainPanel = JPanel(BorderLayout())

        # Button to load Burp XML Export file
        self._loadButton = JButton('Select Burp XML Export File')
        self._loadButton.addActionListener(self.loadButtonTapped)
        self._mainPanel.add(self._loadButton, BorderLayout.PAGE_START)

        # File chooser for Burp XML Export file
        self._fc = JFileChooser()
        self._fc.setDialogTitle("Select Burp XML Export File")

        # Splitpane for table and request/response view
        self._splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT)
        self._mainPanel.add(self._splitpane, BorderLayout.CENTER)

        # Table of log entries
        self._logTable = Table(self)
        self._scrollPane = JScrollPane(self._logTable)
        self._splitpane.setTopComponent(self._scrollPane)

        # Set column width of table
        self._logTable.setAutoResizeMode(JTable.AUTO_RESIZE_OFF)
        self._logTable.getColumnModel().getColumn(0).setPreferredWidth(40)
        self._logTable.getColumnModel().getColumn(1).setPreferredWidth(60)
        self._logTable.getColumnModel().getColumn(2).setPreferredWidth(70)
        self._logTable.getColumnModel().getColumn(3).setPreferredWidth(300)
        self._logTable.getColumnModel().getColumn(4).setPreferredWidth(500)
        self._logTable.getColumnModel().getColumn(5).setPreferredWidth(300)
        self._logTable.getColumnModel().getColumn(6).setPreferredWidth(100)
        self._logTable.getColumnModel().getColumn(7).setPreferredWidth(100)
        self._logTable.getColumnModel().getColumn(8).setPreferredWidth(100)
        self._logTable.getColumnModel().getColumn(9).setPreferredWidth(100)
        self._logTable.getColumnModel().getColumn(10).setPreferredWidth(230)
        self._logTable.getColumnModel().getColumn(11).setMaxWidth(100000)

        # Tabs with request and response viewers
        self._tabs = JTabbedPane()
        self._requestViewer = callbacks.createMessageEditor(self, False)
        self._responseViewer = callbacks.createMessageEditor(self, False)
        self._tabs.addTab("Request", self._requestViewer.getComponent())
        self._tabs.addTab("Response", self._responseViewer.getComponent())
        self._splitpane.setBottomComponent(self._tabs)

        # Customize UI components
        self._callbacks.customizeUiComponent(self._mainPanel)
        self._callbacks.customizeUiComponent(self._splitpane)
        self._callbacks.customizeUiComponent(self._logTable)
        self._callbacks.customizeUiComponent(self._scrollPane)
        self._callbacks.customizeUiComponent(self._tabs)

        # Add the custom tab to Burp's UI
        self._callbacks.addSuiteTab(self)

        return

    """
		Helper Functions
	"""

    def loadButtonTapped(self, actionEvent):

        # Display the file chooser dialog
        retVal = self._fc.showOpenDialog(None)

        if retVal == JFileChooser.APPROVE_OPTION:
            self._file = self._fc.getSelectedFile()
            self.resetList()  # clear the table from all previous entries
            self.parseXML(
                self._file)  # parse the file and load all entries to the table
        else:
            print("Open command cancelled by user.")

    def parseXML(self, file):

        # Initialize XML stuff
        dbFactory = DocumentBuilderFactory.newInstance()
        dBuilder = dbFactory.newDocumentBuilder()
        doc = dBuilder.parse(file)
        doc.getDocumentElement().normalize()

        # All entries in Burp's XML Export File have tag <item>...</item>
        nodeList = doc.getElementsByTagName("item")

        # for i in reversed(range(0, nodeList.getLength())):
        for i in range(0, nodeList.getLength()):
            node = nodeList.item(i)

            if node.getNodeType() == Node.ELEMENT_NODE:

                request = node.getElementsByTagName("request").item(
                    0).getTextContent()
                response = node.getElementsByTagName("response").item(
                    0).getTextContent()

                request_isBase64 = node.getElementsByTagName("request").item(
                    0).getAttribute("base64")
                response_isBase64 = node.getElementsByTagName("response").item(
                    0).getAttribute("base64")

                if request_isBase64 == "true":
                    request = Base64.getDecoder().decode(request)

                if response_isBase64 == "true":
                    response = Base64.getDecoder().decode(response)

                info = {
                    "time":
                    node.getElementsByTagName("time").item(0).getTextContent(),
                    "url":
                    node.getElementsByTagName("url").item(0).getTextContent(),
                    "host":
                    node.getElementsByTagName("host").item(0).getTextContent(),
                    "port":
                    node.getElementsByTagName("port").item(0).getTextContent(),
                    "protocol":
                    node.getElementsByTagName("protocol").item(
                        0).getTextContent(),
                    "method":
                    node.getElementsByTagName("method").item(
                        0).getTextContent(),
                    "path":
                    node.getElementsByTagName("path").item(0).getTextContent(),
                    "extension":
                    node.getElementsByTagName("extension").item(
                        0).getTextContent(),
                    "request":
                    request,
                    "status":
                    node.getElementsByTagName("status").item(
                        0).getTextContent(),
                    "responselength":
                    node.getElementsByTagName("responselength").item(
                        0).getTextContent(),
                    "mimetype":
                    node.getElementsByTagName("mimetype").item(
                        0).getTextContent(),
                    "response":
                    response,
                    "comment":
                    node.getElementsByTagName("comment").item(
                        0).getTextContent(),
                    "highlight":
                    ""
                }

                logEntry = LogEntry(info)

                # Remove GET parameters from path component
                # Path component usually looks like this: /some/path/index.html?q=foo&z=faa
                info["path"] = info["path"].split("?")[0]

                # Extract GET parameters
                params = []
                for param in self._helpers.analyzeRequest(
                        logEntry).getParameters():
                    if param.getType() == IParameter.PARAM_URL:
                        params.append("{}={}".format(param.getName(),
                                                     param.getValue()))
                info["params"] = "&".join(params)

                self.addLogEntryToList(logEntry)

    def addLogEntryToList(self, logEntry):
        self._lock.acquire()
        row = self._log.size()
        self._log.add(logEntry)
        self.fireTableRowsInserted(row, row)
        self._lock.release()

    def resetList(self):
        self._lock.acquire()
        self._log.clear()
        self.fireTableRowsInserted(0, 0)
        self._lock.release()

    """
		Implements ITab
	"""

    def getTabCaption(self):
        return "Burp XML Export Viewer"

    def getUiComponent(self):
        return self._mainPanel

    """
		Extends AbstractTableModel
	"""

    def getRowCount(self):
        try:
            return self._log.size()
        except:
            return 0

    def getColumnCount(self):
        return 12

    def getColumnName(self, columnIndex):
        if columnIndex == 0:
            return "#"
        if columnIndex == 1:
            return "Method"
        if columnIndex == 2:
            return "Protocol"
        if columnIndex == 3:
            return "Host"
        if columnIndex == 4:
            return "Path"
        if columnIndex == 5:
            return "Parameters"
        if columnIndex == 6:
            return "Status"
        if columnIndex == 7:
            return "Length"
        if columnIndex == 8:
            return "MIME type"
        if columnIndex == 9:
            return "Extension"
        if columnIndex == 10:
            return "Time"
        if columnIndex == 11:
            return "Comment"

        return ""

    def getValueAt(self, rowIndex, columnIndex):
        logEntry = self._log.get(rowIndex)

        if columnIndex == 0:
            return "{}".format(rowIndex)
        if columnIndex == 1:
            return logEntry._info["method"]
        if columnIndex == 2:
            return logEntry._info["protocol"]
        if columnIndex == 3:
            return logEntry.getHttpService().getHost()
        if columnIndex == 4:
            return logEntry._info["path"]
        if columnIndex == 5:
            return logEntry._info["params"]
        if columnIndex == 6:
            return logEntry._info["status"]
        if columnIndex == 7:
            return logEntry._info["responselength"]
        if columnIndex == 8:
            return logEntry._info["mimetype"]
        if columnIndex == 9:
            return logEntry._info["extension"]
        if columnIndex == 10:
            return logEntry._info["time"]
        if columnIndex == 11:
            return logEntry._info["comment"]

        return ""

    """
		Implements IMessageEditorController
		Allows request and response viewers to obtain details about the messages being displayed
	"""

    def getHttpService(self):
        return self._currentlyDisplayedItem.getHttpService()

    def getRequest(self):
        return self._currentlyDisplayedItem.getRequest()

    def getResponse(self):
        return self._currentlyDisplayedItem.getResponse()
コード例 #13
0
class BurpExtender(IBurpExtender, ITab):

    #
    # implement IBurpExtender
    #
    def hello(self):
        return "hello"

    def process_file(self, file):
        freshrows = []
        # return list of list of file parts
        for url in file:
            result = urlparse(url)
            scheme = result[0]
            domain = result[0]
            path = result[0]
            params = ''
            query = ''
            fragment = ''
            next = [scheme, domain, path, params, query, fragment]
            freshrows.append(next)
        return freshrows

    def registerExtenderCallbacks(self, callbacks):

        # set our extension name
        callbacks.setExtensionName("Hello world extension")

        # obtain our output and error streams
        stdout = PrintWriter(callbacks.getStdout(), True)
        stderr = PrintWriter(callbacks.getStderr(), True)

        # write a message to our output stream
        stdout.println("Hello output")

        # write a message to our error stream
        stderr.println("Hello errors")

        # write a message to the Burp alerts tab
        callbacks.issueAlert("Hello alerts")

        #create and populate a jtable:
        initial_row = [
            'http', 'www.meetup.com',
            'PyMNtos-Twin-Cities-Python-User-Group/events/267977020/', '', '',
            ''
        ]
        self.fileTable = JTable(ResourceTableModel(initial_row))
        # set up the Tab:

        self.infoPanel = JPanel()
        footerPanel = JPanel()

        footerPanel.add(JLabel("by mcgyver5 "))
        self._chooseFileButton = JButton("OPEN Local FILE",
                                         actionPerformed=self.fileButtonClick)
        self.infoPanel.add(JLabel("INFORMATION PANE"))

        self.infoPanel.add(self._chooseFileButton)
        scrollpane = JScrollPane(self.fileTable)
        ## this is a split inside the top component
        topPane = JSplitPane(JSplitPane.VERTICAL_SPLIT)
        topPane.setTopComponent(self.infoPanel)
        topPane.setBottomComponent(scrollpane)
        self._chooseFileButton.setEnabled(True)
        self._splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT)
        self._splitpane.setTopComponent(topPane)
        self._splitpane.setBottomComponent(footerPanel)
        callbacks.addSuiteTab(self)

    def populateTableModel(self, results):
        tableModel = self.fileTable.getModel()
        for row in results:
            tableModel.addRow(row)

    def fileButtonClick(self, callbacks):
        fileTypeList = ["csv", "txt", "json"]
        txtFilter = FileNameExtensionFilter("txt", fileTypeList)
        fileChooser = JFileChooser()
        fileChooser.addChoosableFileFilter(txtFilter)
        result = fileChooser.showOpenDialog(self._splitpane)

        if result == JFileChooser.APPROVE_OPTION:
            f = fileChooser.getSelectedFile()
            fileName = f.getPath()
            self.populateTableModel(f)

    ## Implement ITab:
    def getTabCaption(self):
        return "Import URLs"

    def getUiComponent(self):
        return self._splitpane
コード例 #14
0
    def create(self):

        # Estilo general para todas las sub-tab.
        gBC = GridBagConstraints()
        gBC.fill = GridBagConstraints.BOTH
        gBC.ipadx = 5
        gBC.ipady = 5
        gBC.insets = Insets(0, 5, 5, 5)
        gBC.weightx = 0.5
        #gBC.weighty = 0.7

        #######################################
        ###   Creamos la primera sub-tab. (MASHUP)
        #######################################
        tab_1 = JPanel(GridBagLayout())
        tab_1_jlabelAyuda = JLabel(
            '<html><i>&#8226Tip: This Mashup receive one or more keywords in order to generate a list of possible passwords</i></html>'
        )
        tab_1_jlabelAyuda.setFont(Font("Serif", 0, 12))

        gBC.gridx = 0
        gBC.gridy = 0
        tab_1.add(
            JLabel('<html><font color=green><i>Income:</i></font></html>'),
            gBC)

        gBC.gridy = 1
        tab_1.add(JLabel('<html><b>&#8226 Name:</b></html>'), gBC)
        gBC.gridy = 2
        tab_1.add(self._tab1_nombre, gBC)

        gBC.gridy = 3
        tab_1.add(JLabel('<html><b>&#8226 Surname:</b></html>'), gBC)
        gBC.gridy = 4
        tab_1.add(self._tab1_apellido, gBC)

        gBC.gridy = 5
        tab_1.add(JLabel('<html><b>&#8226 Birthdate: (DDMMYYYY)</b></html>'),
                  gBC)
        gBC.gridy = 6
        tab_1.add(self._tab1_FNacimiento, gBC)

        gBC.gridy = 7
        tab_1.add(JLabel('<html><b>&#8226 Pet:</b></html>'), gBC)
        gBC.gridy = 8
        tab_1.add(self._tab1_mascota, gBC)

        gBC.gridy = 9
        tab_1.add(JLabel('<html><b>&#8226 Anyother:</b></html>'), gBC)
        gBC.gridy = 10
        tab_1.add(self._tab1_otro, gBC)

        gBC.gridy = 11
        tab_1.add(JLabel('<html><b>&#8226 Passwd Min Size:</b></html>'), gBC)
        gBC.gridy = 12
        tab_1.add(self._tab1_minsize, gBC)

        gBC.gridy = 13
        tab_1.add(JLabel('<html><b>&#8226 Passwd Max Size:</b></html>'), gBC)
        gBC.gridy = 14
        tab_1.add(self._tab1_maxsize, gBC)

        gBC.gridy = 15
        tab_1.add(
            JLabel(
                '<html><b>&#8226 Especial Chars: (comma separated)</b></html>'
            ), gBC)
        gBC.gridy = 16
        tab_1.add(self._tab1_specialchars, gBC)

        gBC.gridy = 17
        tab_1.add(self._tab1_transformations, gBC)

        gBC.gridy = 18
        tab_1.add(self._tab1_firstcapital, gBC)

        gBC.gridy = 19
        tab_1.add(JButton('Mashup!', actionPerformed=self.mashup), gBC)

        gBC.gridy = 20
        gBC.gridwidth = 3
        tab_1.add(JSeparator(), gBC)
        gBC.gridwidth = 1

        gBC.gridy = 21
        gBC.gridwidth = 3
        tab_1.add(tab_1_jlabelAyuda, gBC)
        gBC.gridwidth = 1

        gBC.gridx = 1
        gBC.gridy = 0
        gBC.gridheight = 20
        gBC.weightx = 0
        tab_1.add(JSeparator(SwingConstants.VERTICAL), gBC)
        gBC.gridheight = 1
        gBC.weightx = 0.5

        gBC.gridx = 2
        gBC.gridy = 0
        tab_1.add(
            JLabel('<html><font color=green><i>Outcome:</i></font></html>'),
            gBC)

        gBC.gridy = 1
        gBC.gridwidth = 2
        gBC.gridheight = 18
        tab_1.add(self._tab1_feedback_sp, gBC)
        gBC.gridwidth = 1
        gBC.gridheight = 1

        gBC.gridy = 19
        tab_1.add(
            JButton('Copy to clipboard!', actionPerformed=self.cpy_clipboard),
            gBC)

        #######################################
        ###   Creamos la segunda sub-tab. (REDIRECT)
        #######################################
        tab_2 = JPanel(GridBagLayout())
        tab_2_jlabelAyuda = JLabel(
            '<html><i>&#8226Tip: This Redirect receive a pair of hosts x,y in order to redirect from x to y.</i></html>'
        )
        tab_2_jlabelAyuda.setFont(Font("Serif", 0, 12))

        gBC.gridx = 0
        gBC.gridy = 0
        tab_2.add(
            JLabel('<html><b>&#8226 From: (i.e. www.facebook.com)</b></html>'),
            gBC)
        gBC.gridx = 1
        gBC.gridy = 0
        tab_2.add(self._tab2_JTFa, gBC)

        gBC.gridx = 2
        gBC.gridy = 0
        tab_2.add(
            JLabel('<html><b>&#8226 To: (i.e. www.myhomepage.es)</b></html>'),
            gBC)
        gBC.gridx = 3
        gBC.gridy = 0
        tab_2.add(self._tab2_JTFaa, gBC)

        gBC.gridx = 0
        gBC.gridy = 1
        gBC.gridwidth = 4
        tab_2.add(JSeparator(), gBC)
        gBC.gridwidth = 1

        gBC.gridx = 0
        gBC.gridy = 2
        tab_2.add(JLabel('<html><b>&#8226 From:</b></html>'), gBC)
        gBC.gridx = 1
        gBC.gridy = 2
        tab_2.add(self._tab2_JTFb, gBC)

        gBC.gridx = 2
        gBC.gridy = 2
        tab_2.add(JLabel('<html><b>&#8226 To:</b></html>'), gBC)
        gBC.gridx = 3
        gBC.gridy = 2
        tab_2.add(self._tab2_JTFbb, gBC)

        gBC.gridx = 0
        gBC.gridy = 3
        gBC.gridwidth = 4
        tab_2.add(self._tab2_boton, gBC)
        gBC.gridwidth = 1

        gBC.gridx = 0
        gBC.gridy = 4
        gBC.gridwidth = 4
        gBC.insets = Insets(100, 10, 5, 10)
        tab_2.add(JSeparator(), gBC)
        gBC.gridwidth = 1
        gBC.insets = Insets(5, 10, 5, 10)

        gBC.gridx = 0
        gBC.gridy = 5
        gBC.gridwidth = 4
        tab_2.add(tab_2_jlabelAyuda, gBC)
        gBC.gridwidth = 1

        #######################################
        ###   Creamos la tercera sub-tab. (LOADER)
        #######################################
        tab_3 = JPanel(GridBagLayout())
        tab_3_jlabelAyuda = JLabel(
            '<html><i>&#8226Tip: This Loader receive a list of Hosts or IPs that will be added to the Burp Scope.</i></html>'
        )
        tab_3_jlabelAyuda.setFont(Font("Serif", 0, 12))

        gBC.gridx = 0
        gBC.gridy = 0
        tab_3.add(
            JLabel(
                '<html><font color=green><i>List of targets: (i.e. http://www.mytargetweb.com)</i></font></html>'
            ), gBC)
        gBC.gridy = 1
        gBC.gridheight = 10
        gBC.weighty = 0.5
        tab_3.add(self._tab3_urls_sp, gBC)
        gBC.gridheight = 1
        gBC.weighty = 0
        gBC.gridy = 11
        tab_3.add(
            JButton('Load Into Target => Scope!', actionPerformed=self.loader),
            gBC)

        gBC.gridy = 12
        gBC.gridwidth = 5
        gBC.insets = Insets(100, 10, 5, 10)
        tab_3.add(JSeparator(), gBC)
        gBC.gridwidth = 1
        gBC.insets = Insets(5, 10, 5, 10)

        gBC.gridy = 13
        tab_3.add(tab_3_jlabelAyuda, gBC)

        #######################################
        ###   Creamos la cuarta sub-tab. (HEADERS)
        #######################################
        tab_4_jlabelAyuda = JLabel(
            "<html><i>&#8226Tip: This Headers records all unique headers that appear in every host, check out the security headers.</i></html>"
        )
        tab_4_jlabelAyuda.setFont(Font("Serif", 0, 12))

        tab_4_jLabelRecomendacion = JLabel(
            "<html>&#8226<b>Server</b>: Don't give away much information.<br> &#8226<b>Content-Security-Policy</b>: Protect your site from XSS attacks by whitelisting sources of approved content.<br> &#8226<b>Strict-Transport-Security</b>: Enforce the browser to use HTTPS.<br> &#8226<b>Public-Key-Pins</b>: Protect your site from MITM attacks.<br> &#8226<b>X-Content-Type-Options</b>: the valid value is -> nosniff .<br> &#8226<b>X-Frame-Options</b>: tells the browser whether you want to allow your site to be framed or not.<br> &#8226<b>X-XSS-Protection</b>: the best value is -> 1; mode=block .</html>"
        )
        tab_4_jLabelRecomendacion.setFont(Font("Dialog", 0, 13))

        tab_4 = JPanel(GridBagLayout())
        splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT)
        tab_4_top = JPanel(GridBagLayout())
        tab_4_bottom = JPanel(GridBagLayout())

        gBC_table = GridBagConstraints()
        gBC_table.fill = GridBagConstraints.BOTH
        gBC_table.ipadx = 5
        gBC_table.ipady = 5
        gBC_table.insets = Insets(5, 10, 5, 10)
        gBC_table.weightx = 1
        gBC_table.weighty = 1

        tabla_datos = []
        tabla_headers = ('Severity', 'Header', 'Value', 'Host')
        self._tab4_tabla_model = DefaultTableModel(tabla_datos, tabla_headers)
        tabla_ej = JTable(self._tab4_tabla_model)
        tabla_example = JScrollPane(tabla_ej,
                                    JScrollPane.VERTICAL_SCROLLBAR_AS_NEEDED,
                                    JScrollPane.HORIZONTAL_SCROLLBAR_AS_NEEDED)

        gBC_table.gridx = 0
        gBC_table.gridy = 0
        gBC_table.gridheight = 5
        tab_4_top.add(tabla_example, gBC_table)
        gBC_table.gridheight = 1

        gBC_table.weightx = 0.5
        gBC_table.weighty = 0
        gBC_table.gridwidth = 2
        gBC_table.gridx = 0
        gBC_table.gridy = 0
        tab_4_bottom.add(JSeparator(), gBC_table)
        gBC_table.gridy = 1
        tab_4_bottom.add(tab_4_jlabelAyuda, gBC_table)
        gBC_table.gridy = 2
        tab_4_bottom.add(tab_4_jLabelRecomendacion, gBC_table)

        splitpane.setTopComponent(tab_4_top)
        splitpane.setBottomComponent(tab_4_bottom)
        gBC_table.weightx = 1
        gBC_table.weighty = 1
        gBC_table.gridx = 0
        gBC_table.gridy = 0
        tab_4.add(splitpane, gBC_table)

        #######################################
        ###   Creamos la quinta sub-tab. (ACTIVE SCAN)
        #######################################
        tab_5 = JPanel(GridBagLayout())
        tab_5_jlabelAyuda = JLabel(
            '<html><i>&#8226Tip: This Quick Scan receive a list of targets and launch an active scan.</i></html>'
        )
        tab_5_jlabelAyuda.setFont(Font("Serif", 0, 12))
        tab_5_jlabelWarning = JLabel(
            '<html><font color=red><i>&#8226Warning: Active scanning generates large numbers of requests which are malicious in form and which may result in compromise of the application. You should use this scanning mode with caution, only with the explicit permission of the application owner. For more information, read the documentation of active scan, Burp Suite.</font></i></html>'
        )
        tab_5_jlabelWarning.setFont(Font("Dialog", 0, 13))

        gBC.gridx = 0
        gBC.gridy = 0
        tab_5.add(
            JLabel(
                '<html><font color=green><i>List of targets: (i.e. http://192.168.1.1/index.html)</i></font></html>'
            ), gBC)
        gBC.gridy = 1
        gBC.gridheight = 8
        gBC.weighty = 0.5
        tab_5.add(self._tab5_target_sp, gBC)
        gBC.gridheight = 1
        gBC.weighty = 0
        gBC.gridy = 9
        tab_5.add(JButton('Launch Scan!', actionPerformed=self.do_active_scan),
                  gBC)

        gBC.gridy = 10
        gBC.gridwidth = 5
        gBC.insets = Insets(100, 10, 5, 10)
        tab_5.add(JSeparator(), gBC)
        gBC.gridwidth = 1
        gBC.insets = Insets(5, 10, 5, 10)

        gBC.gridy = 11
        tab_5.add(tab_5_jlabelAyuda, gBC)
        gBC.gridy = 12
        tab_5.add(tab_5_jlabelWarning, gBC)

        #######################################
        ###   Creamos la ultima sub-tab.
        #######################################
        tab_about = JPanel(GridBagLayout())

        gBC_about = GridBagConstraints()
        gBC_about.fill = GridBagConstraints.HORIZONTAL
        gBC_about.ipadx = 5
        gBC_about.ipady = 5
        gBC_about.insets = Insets(5, 10, 5, 10)
        gBC_about.weightx = 1
        gBC_about.weighty = 1

        Jlabel1 = JLabel('<html><b>Plug-in L-Tools</b></html>')
        Jlabel1.setFont(Font("Dialog", 1, 18))
        jlabel2 = JLabel(
            '<html>This Plug-in provides utilities for pentesters, researchers and developers, in order to support their work.</html>'
        )
        jlabel3 = JLabel('<html><b>CC-BY 4.0, 2017. Gino Angles</b></html>')
        jlabel3.setFont(Font("Dialog", 1, 14))
        jlabel4 = JLabel('<html><b>License</b></html>')
        jlabel4.setFont(Font("Dialog", 1, 14))
        jlabel5 = JLabel(
            '<html><img alt="Licensed under a Creative Commons BY" style="border-width:0" src="https://licensebuttons.net/l/by/4.0/88x31.png"></html>'
        )
        jlabel6 = JLabel(
            '<html>This work is licensed under a <a rel="license" href="http://creativecommons.org/licenses/by/4.0/">Creative Commons Attribution 4.0 International License</a>.</html>'
        )
        jlabel7 = JLabel('<html><b>Dependencies</b></html>')
        jlabel7.setFont(Font("Dialog", 1, 14))
        jlabel8 = JLabel('Jython +2.7')
        jlabel9 = JLabel('http://www.jython.org')

        gBC_about.gridx = 0
        gBC_about.gridy = 0
        tab_about.add(Jlabel1, gBC_about)
        gBC_about.gridy = 1
        tab_about.add(jlabel2, gBC_about)
        gBC_about.gridy = 2
        tab_about.add(jlabel3, gBC_about)

        gBC_about.gridy = 3
        gBC_about.gridwidth = 5
        tab_about.add(JSeparator(), gBC_about)
        gBC_about.gridwidth = 1

        gBC_about.gridy = 4
        tab_about.add(jlabel4, gBC_about)
        gBC_about.gridy = 5
        tab_about.add(jlabel5, gBC_about)
        gBC_about.gridy = 6
        tab_about.add(jlabel6, gBC_about)

        gBC_about.gridy = 7
        gBC_about.gridwidth = 5
        tab_about.add(JSeparator(), gBC_about)
        gBC_about.gridwidth = 1

        gBC_about.gridy = 8
        tab_about.add(jlabel7, gBC_about)
        gBC_about.gridy = 9
        tab_about.add(jlabel8, gBC_about)
        gBC_about.gridy = 10
        tab_about.add(jlabel9, gBC_about)

        # Añadimos los sub-tab al contenedor y lo devolvemos.
        self.contenedor.addTab('Mashup', tab_1)
        self.contenedor.addTab('Redirect', tab_2)
        self.contenedor.addTab('Loader', tab_3)
        self.contenedor.addTab('Headers', tab_4)
        self.contenedor.addTab('Quick Scan', tab_5)
        self.contenedor.addTab('About', tab_about)

        return self.contenedor
コード例 #15
0
ファイル: warstory.py プロジェクト: mcgyver5/warstory
class BurpExtender(IBurpExtender, ITab):

    #
    # implement IBurpExtender
    #

    def registerExtenderCallbacks(self, callbacks):

        # set our extension name
        callbacks.setExtensionName("War Story")

        # obtain our output stream
        self._stdout = PrintWriter(callbacks.getStdout(), True)

        # write a message to our output stream
        self._stdout.println("Loading WarStory")

        # write a message to the Burp alerts tab
        callbacks.issueAlert("Hello alerts")
        label = JLabel("INFO PANEL")
        self.infoPanel = JPanel()
        footerPanel = JPanel()
        footerPanel.add(JLabel("by Tim mcgyver5 McGuire"))
        self._chooseFileButton = JButton("OPEN WAR FILE",
                                         actionPerformed=self.fileButtonClick)
        self.infoPanel.add(JLabel("THIS IS INFORMATION PANE"))
        self.infoPanel.add(self._chooseFileButton)
        # iaap.war|web.xml|axServlet|/skuppy/axservlet.do|
        self._chooseFileButton.setEnabled(True)
        initial_row = ['a', 'bb', 'ccc', 'ddd', 'eeee']
        self.fileTable = JTable(ResourceTableModel(initial_row))
        scrollpane = JScrollPane(self.fileTable)

        ## this is a split inside the top component
        topPane = JSplitPane(JSplitPane.VERTICAL_SPLIT)

        topPane.setTopComponent(self.infoPanel)
        topPane.setBottomComponent(scrollpane)

        # split the top panel into a Panel and a JScrollPane

        self._splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT)
        self._splitpane.setTopComponent(topPane)
        self._splitpane.setBottomComponent(footerPanel)

        callbacks.addSuiteTab(self)

    def populateJTable(self, f):
        filename = f.getPath()
        tableModel = self.fileTable.getModel()
        test_row = ["a", "b", "doo", "dah", "dob"]
        re = Resource("Servlet", "bingServlet", "bingservlet.do", [], [],
                      "GET")
        self._stdout.println("populatin table model")
        tableModel.addRow(test_row)

    def fileButtonClick(self, e):

        fileTypeList = ["war", "ear", "zip"]
        warFilter = FileNameExtensionFilter("war", fileTypeList)
        fileChooser = JFileChooser()
        fileChooser.addChoosableFileFilter(warFilter)
        result = fileChooser.showOpenDialog(self._splitpane)

        if result == JFileChooser.APPROVE_OPTION:
            f = fileChooser.getSelectedFile()
            fileName = f.getPath()
            self.populateJTable(f)

    # Implement ITab
    def getTabCaption(self):
        return "War Story"

    def getUiComponent(self):
        return self._splitpane
コード例 #16
0
class BurpExtender(IBurpExtender, IContextMenuFactory, ITab, ComponentListener,
                   ActionListener, MouseAdapter):
    # contains the messages to show in the messages table
    _table_data = []

    # contains the messages to translate
    _messages = []

    # used to keep track when to refresh the table
    _reload_table = False

    _sql_file = None

    def registerExtenderCallbacks(self, callbacks):

        self._panel = JPanel()
        self._panel.setLayout(BorderLayout())
        #self._panel.setSize(400,400)

        # sourrounding try\except because Burp is not giving enough info
        try:

            # creating all the UI elements
            # create the split pane
            self._split_pane_horizontal = JSplitPane(
                JSplitPane.HORIZONTAL_SPLIT)
            self._split_panel_vertical = JSplitPane(JSplitPane.VERTICAL_SPLIT)

            # create panels
            self._panel_top = JPanel()
            self._panel_top.setLayout(BorderLayout())
            self._panel_bottom = JPanel()
            self._panel_bottom.setLayout(BorderLayout())
            self._panel_right = JPanel()
            self._panel_right.setLayout(BorderLayout())
            self._panel_request = JPanel()
            self._panel_request.setLayout(BorderLayout())
            self._panel_response = JPanel()
            self._panel_response.setLayout(BorderLayout())

            # create the tabbed pane used to show request\response
            self._tabbed_pane = JTabbedPane(JTabbedPane.TOP)

            # create the tabbed pane used to show aslan++\concretization file
            self._tabbed_pane_editor = JTabbedPane(JTabbedPane.TOP)

            # create the bottom command for selecting the SQL file and
            # generating the model
            self._button_generate = JButton(
                'Generate!', actionPerformed=self._generate_model)
            self._button_save = JButton('Save',
                                        actionPerformed=self._save_model)
            self._button_select_sql = JButton(
                'Select SQL', actionPerformed=self._select_sql_file)
            self._text_field_sql_file = JTextField(20)

            self._panel_bottom_commands = JPanel()
            layout = GroupLayout(self._panel_bottom_commands)
            layout.setAutoCreateGaps(True)
            layout.setAutoCreateContainerGaps(True)
            seq_layout = layout.createSequentialGroup()
            seq_layout.addComponent(self._text_field_sql_file)
            seq_layout.addComponent(self._button_select_sql)
            seq_layout.addComponent(self._button_generate)
            seq_layout.addComponent(self._button_save)
            layout.setHorizontalGroup(seq_layout)

            # create the message editors that will be used to show request and response
            self._message_editor_request = callbacks.createMessageEditor(
                None, True)
            self._message_editor_response = callbacks.createMessageEditor(
                None, True)

            # create the table that will be used to show the messages selected for
            # the translation

            self._columns_names = ('Host', 'Method', 'URL')
            dataModel = NonEditableModel(self._table_data, self._columns_names)
            self._table = JTable(dataModel)
            self._scrollPane = JScrollPane()
            self._scrollPane.getViewport().setView((self._table))

            popmenu = JPopupMenu()
            delete_item = JMenuItem("Delete")
            delete_item.addActionListener(self)
            popmenu.add(delete_item)
            self._table.setComponentPopupMenu(popmenu)
            self._table.addMouseListener(self)

            # add all the elements
            self._panel_request.add(
                self._message_editor_request.getComponent())
            self._panel_response.add(
                self._message_editor_response.getComponent())

            self._tabbed_pane.addTab("Request", self._panel_request)
            self._tabbed_pane.addTab("Response", self._panel_response)

            self._panel_top.add(self._scrollPane, BorderLayout.CENTER)

            self._panel_bottom.add(self._tabbed_pane, BorderLayout.CENTER)
            scroll = JScrollPane(self._panel_bottom)

            self._panel_right.add(self._tabbed_pane_editor,
                                  BorderLayout.CENTER)
            self._panel_right.add(self._panel_bottom_commands,
                                  BorderLayout.PAGE_END)

            self._split_panel_vertical.setTopComponent(self._panel_top)
            self._split_panel_vertical.setBottomComponent(scroll)
            self._split_pane_horizontal.setLeftComponent(
                self._split_panel_vertical)
            self._split_pane_horizontal.setRightComponent(self._panel_right)

            self._panel.addComponentListener(self)
            self._panel.add(self._split_pane_horizontal)

            self._callbacks = callbacks
            callbacks.setExtensionName("WAFEx")
            callbacks.addSuiteTab(self)
            callbacks.registerContextMenuFactory(self)
        except Exception as e:
            exc_type, exc_obj, exc_tb = sys.exc_info()
            fname = os.path.split(exc_tb.tb_frame.f_code.co_filename)[1]
            print(exc_type, fname, exc_tb.tb_lineno)

    def getTabCaption(self):
        return "WAFEx"

    def getUiComponent(self):
        try:
            Platform.runLater(EditorTabUI(self))
            return self._panel
        except Exception as e:
            exc_type, exc_obj, exc_tb = sys.exc_info()
            fname = os.path.split(exc_tb.tb_frame.f_code.co_filename)[1]
            print(exc_type, fname, exc_tb.tb_lineno)

    def componentShown(self, e):
        self._split_pane_horizontal.setDividerLocation(0.25)
        # populate the table with the selected requests\response
        try:
            if self._reload_table:
                print("reload")
                self._table_data = [
                ]  # empty _table_data (not too cool but quick)
                for c in self._messages:
                    msg = c[0]
                    http_request = converter._byte_array_to_string(
                        msg.getRequest())
                    request_parser = HttpParser()
                    request_parser.execute(http_request, len(http_request))

                    host = msg.getHttpService().getHost()
                    page = request_parser.get_url()
                    method = request_parser.get_method()

                    tmp = [host, method, page]
                    self._table_data += [tmp]
                self._table.getModel().setDataVector(self._table_data,
                                                     self._columns_names)
                self._reload_table = False
        except Exception as e:
            print(e)

    def componentHidden(self, e):
        return

    def componentMoved(self, e):
        return

    def componentResized(self, e):
        self._split_pane_horizontal.setDividerLocation(0.25)

    def createMenuItems(self, invocation):
        ret = []
        try:
            if (invocation.getInvocationContext() ==
                    invocation.CONTEXT_TARGET_SITE_MAP_TABLE):
                menu = JMenuItem("Send to WAFEx")
                messages = invocation.getSelectedMessages()

                def listener(e):
                    """ Generates a new WAFEx model. """
                    #self._generateWAFExModel(messages)
                    self._addToGeneration(messages)

                menu.addActionListener(listener)
                ret.append(menu)
        except Exception as e:
            print(e)
        return ret

    def mouseClicked(self, e):
        """ Positions the Aslan++ editor to the selected request position. """
        try:
            index = self._table.getSelectedRow()
            c = self._messages[index]
            print(len(c))
            message = c[0]
            tag = c[1]
            self._message_editor_request.setMessage(message.getRequest(), True)
            self._message_editor_response.setMessage(message.getResponse(),
                                                     False)
            if tag != None:
                document = self._jfxp_aslanpp._editor.getText()
                start, end = self._search_tag_position(tag, document)
                self._jfxp_aslanpp._editor.moveTo(start)
                self._jfxp_aslanpp._editor.selectRange(start, end)
                self._jfxp_aslanpp._editor.requestFollowCaret()
                self._jfxp_aslanpp._editor.requestFocus()
        except Exception as e:
            print(e)

    def actionPerformed(self, e):
        """ Performs the delete action. """
        try:
            index = self._table.getSelectedRow()
            del self._table_data[index]
            del self._messages[index]
            self._table.getModel().setDataVector(self._table_data,
                                                 self._columns_names)
        except Exception as e:
            print(e)

    def _search_tag_position(self, tag, text):
        """ Searches for a particular tag in a given text and return its position. """
        pattern = self._search_pattern.format(tag)
        for m in re.finditer(pattern, text):
            return m.start(), m.end()

    def _save_model(self, e):
        """ Saves the current Aslan++ model and concretization file. """
        try:
            chooseFile = JFileChooser()
            filter_ = FileNameExtensionFilter("txt files", ["txt"])
            chooseFile.addChoosableFileFilter(filter_)

            ret = chooseFile.showDialog(self._panel, "Choose file")

            if ret == JFileChooser.APPROVE_OPTION:
                self._model_name = chooseFile.getSelectedFile().getPath()
                with open("{}.aslan++".format(self._model_name), "w") as f:
                    skeleton = self._jfxp_aslanpp._editor.getText()
                    skeleton = skeleton.replace("@filename",
                                                basename(self._model_name))
                    f.write(skeleton)
                print("model created")

                with open("{}.txt".format(self._model_name), "w") as f:
                    f.write(self._jfxp_concretization._editor.getText())

        except Exception as e:
            print(e)

    def _select_sql_file(self, e):
        """ Shows a JFileChooser dialog to select the SQL file to use for creating
        the model. """
        try:
            chooseFile = JFileChooser()
            filter_ = FileNameExtensionFilter("txt files", ["txt"])
            chooseFile.addChoosableFileFilter(filter_)

            ret = chooseFile.showDialog(self._panel, "Choose file")

            if ret == JFileChooser.APPROVE_OPTION:
                self._sql_file = chooseFile.getSelectedFile().getPath()
            else:
                self._sql_file = None
            self._text_field_sql_file.setText("" + self._sql_file)
        except Exception as e:
            print(e)

    def _addToGeneration(self, messages):
        for msg in messages:
            self._messages += [[msg, None]]
        self._reload_table = True

    def _generate_model(self, e):
        if len(self._messages) <= 0:
            frame = JFrame("Error")
            JOptionPane.showMessageDialog(frame, "No messages!", "Error",
                                          JOptionPane.ERROR_MESSAGE)
            return
        if self._sql_file == None:
            frame = JFrame("Error")
            replay = JOptionPane.showConfirmDialog(
                frame, "No SQL file selected!\nDo you want to continue?",
                "Info", JOptionPane.YES_NO_OPTION)
            if replay == JOptionPane.NO_OPTION:
                return

        # create a new AslanppModel
        model = AslanppModel()
        # save _sql_file
        model._sql_file = self._sql_file

        for c in self._messages:
            # from byte to char Request and Response
            # for some reason b can be a negative value causing a crash
            # so I put a check to ensure b is in the right range
            msg = c[0]
            if msg.getRequest() == None or msg.getResponse() == None:
                # do not convert empty messages
                continue
            http_request = "".join(
                chr(b) for b in msg.getRequest() if b >= 0 and b <= 256)
            http_response = "".join(
                chr(b) for b in msg.getResponse() if b >= 0 and b <= 256)
            protocol = msg.getHttpService().getProtocol()
            # save the tag number generate by _parseHttpRequestResponse in the _messages array
            c[1] = converter._parseHttpRequestResponse(model, http_request,
                                                       http_response, protocol)

        # generate the ASLan++ code
        self._model, self._concrete = converter._generateWAFExModel(model)
        Platform.runLater(
            UpdateEditor(self._jfxp_aslanpp._editor,
                         self._jfxp_concretization._editor, self._model,
                         self._concrete))
コード例 #17
0
class BurpExtender(IBurpExtender, ISessionHandlingAction, ITab,
                   IContextMenuFactory, IContextMenuInvocation, ActionListener,
                   ITextEditor):

    #
    # implement IBurpExtender
    #

    def registerExtenderCallbacks(self, callbacks):
        # save the helpers for later
        self.helpers = callbacks.getHelpers()

        # set our extension name
        callbacks.setExtensionName("Custom Request Handler")
        callbacks.registerSessionHandlingAction(self)
        callbacks.registerContextMenuFactory(self)
        self._text_editor = callbacks.createTextEditor()
        self._text_editor.setEditable(False)

        #How much loaded the table row
        self.current_column_id = 0

        #GUI
        self._split_main = JSplitPane(JSplitPane.VERTICAL_SPLIT)
        self._split_top = JSplitPane(JSplitPane.HORIZONTAL_SPLIT)
        self._split_top.setPreferredSize(Dimension(100, 50))
        self._split_top.setDividerLocation(700)
        self._split_center = JSplitPane(JSplitPane.VERTICAL_SPLIT)

        boxVertical = swing.Box.createVerticalBox()
        box_top = swing.Box.createHorizontalBox()
        boxHorizontal = swing.Box.createHorizontalBox()
        buttonHorizontal = swing.Box.createHorizontalBox()
        boxVertical.add(boxHorizontal)

        box_regex = swing.Box.createVerticalBox()
        border = BorderFactory.createTitledBorder(LineBorder(Color.BLACK),
                                                  "Extract target strings",
                                                  TitledBorder.LEFT,
                                                  TitledBorder.TOP)
        box_regex.setBorder(border)

        self._add_btn = JButton("Add")
        self._add_btn.addActionListener(self)
        self._remove_btn = JButton("Remove")
        self._remove_btn.addActionListener(self)

        items = [
            'JSON',
            'Header',
        ]
        self._dropdown = JComboBox(items)
        type_panel = JPanel(FlowLayout(FlowLayout.LEADING))
        type_panel.add(JLabel('Type:'))
        type_panel.add(self._dropdown)

        self._jLabel_param = JLabel("Name:")
        self._param_error = JLabel("Name is required")

        self._param_error.setVisible(False)
        self._param_error.setFont(Font(Font.MONOSPACED, Font.ITALIC, 12))
        self._param_error.setForeground(Color.red)

        regex_checkbox = JPanel(FlowLayout(FlowLayout.LEADING))
        self._is_use_regex = JCheckBox("Extract from regex group")
        regex_checkbox.add(self._is_use_regex)
        self._jTextIn_param = JTextField(20)
        self._jLabel_regex = JLabel("Regex:")
        self._jTextIn_regex = JTextField(20)
        self._regex_error = JLabel("No group defined")
        self._regex_error.setVisible(False)
        self._regex_error.setFont(Font(Font.MONOSPACED, Font.ITALIC, 12))
        self._regex_error.setForeground(Color.red)

        self._param_panel = JPanel(FlowLayout(FlowLayout.LEADING))
        self._param_panel.add(self._jLabel_param)
        self._param_panel.add(self._jTextIn_param)
        self._param_panel.add(self._param_error)

        self._regex_panel = JPanel(FlowLayout(FlowLayout.LEADING))
        self._regex_panel.add(self._jLabel_regex)
        self._regex_panel.add(self._jTextIn_regex)
        self._regex_panel.add(self._regex_error)
        button_panel = JPanel(FlowLayout(FlowLayout.LEADING))
        #padding
        button_panel.add(JPanel())
        button_panel.add(JPanel())
        button_panel.add(JPanel())
        button_panel.add(self._add_btn)
        button_panel.add(self._remove_btn)
        box_regex.add(type_panel)
        box_regex.add(self._param_panel)
        box_regex.add(regex_checkbox)
        box_regex.add(self._regex_panel)
        buttonHorizontal.add(button_panel)
        box_regex.add(buttonHorizontal)
        boxVertical.add(box_regex)
        box_top.add(boxVertical)

        box_file = swing.Box.createHorizontalBox()
        checkbox_panel = JPanel(FlowLayout(FlowLayout.LEADING))
        border = BorderFactory.createTitledBorder(
            LineBorder(Color.BLACK), 'Payload Sets [Simple list]',
            TitledBorder.LEFT, TitledBorder.TOP)
        box_file.setBorder(border)

        box_param = swing.Box.createVerticalBox()
        box_param.add(checkbox_panel)

        file_column_names = [
            "Type",
            "Name",
            "Payload",
        ]
        data = []
        self.file_table_model = DefaultTableModel(data, file_column_names)
        self.file_table = JTable(self.file_table_model)
        self.file_table.setAutoResizeMode(JTable.AUTO_RESIZE_OFF)

        column_model = self.file_table.getColumnModel()
        for count in xrange(column_model.getColumnCount()):
            column = column_model.getColumn(count)
            column.setPreferredWidth(160)

        self.file_table.preferredScrollableViewportSize = Dimension(500, 70)
        self.file_table.setFillsViewportHeight(True)

        panel_dropdown = JPanel(FlowLayout(FlowLayout.LEADING))
        self._file_dropdown = JComboBox(items)
        panel_dropdown.add(JLabel('Type:'))
        panel_dropdown.add(self._file_dropdown)
        box_param.add(panel_dropdown)
        box_param.add(JScrollPane(self.file_table))
        callbacks.customizeUiComponent(self.file_table)

        file_param_panel = JPanel(FlowLayout(FlowLayout.LEADING))

        self._file_param = JLabel("Name:")
        self._file_param_text = JTextField(20)

        file_param_panel.add(self._file_param)
        file_param_panel.add(self._file_param_text)
        self._error_message = JLabel("Name is required")
        self._error_message.setVisible(False)
        self._error_message.setFont(Font(Font.MONOSPACED, Font.ITALIC, 12))
        self._error_message.setForeground(Color.red)
        file_param_panel.add(self._error_message)
        box_param.add(file_param_panel)

        box_button_file = swing.Box.createVerticalBox()
        self._file_load_btn = JButton("Load")

        self._file_clear_btn = JButton("Clear")
        self._file_clear_btn.addActionListener(self)
        self._file_load_btn.addActionListener(self)
        box_button_file.add(self._file_load_btn)
        box_button_file.add(self._file_clear_btn)
        box_file.add(box_button_file)
        box_file.add(box_param)
        boxVertical.add(box_file)

        regex_column_names = [
            "Type",
            "Name",
            "Regex",
            "Start at offset",
            "End at offset",
        ]
        #clear target.json
        with open("target.json", "w") as f:
            pass
        data = []
        self.target_table_model = DefaultTableModel(data, regex_column_names)
        self.target_table = JTable(self.target_table_model)
        self.target_table.setAutoResizeMode(JTable.AUTO_RESIZE_OFF)
        column_model = self.target_table.getColumnModel()
        for count in xrange(column_model.getColumnCount()):
            column = column_model.getColumn(count)
            column.setPreferredWidth(100)

        self.target_table.preferredScrollableViewportSize = Dimension(500, 70)
        self.target_table.setFillsViewportHeight(True)
        callbacks.customizeUiComponent(self.target_table)
        callbacks.customizeUiComponent(boxVertical)
        table_panel = swing.Box.createVerticalBox()
        table_panel.add(JScrollPane(self.target_table))
        box_top.add(table_panel)

        self._jScrollPaneOut = JScrollPane()
        #self._split_main.setBottomComponent(self._jScrollPaneOut)
        self._split_main.setBottomComponent(self._text_editor.getComponent())
        self._split_main.setTopComponent(box_top)
        self._split_main.setDividerLocation(450)
        callbacks.customizeUiComponent(self._split_main)
        callbacks.addSuiteTab(self)
        return

    def getTabCaption(self):
        return "CRH"

    def getUiComponent(self):
        return self._split_main

    def createMenuItems(self, invocation):
        menu = []
        ctx = invocation.getInvocationContext()
        menu.append(
            swing.JMenuItem("Send to CRH",
                            None,
                            actionPerformed=lambda x, inv=invocation: self.
                            menu_action(inv)))
        return menu if menu else None

    #
    # Implementation of Menu Action
    #
    def menu_action(self, invocation):
        try:
            invMessage = invocation.getSelectedMessages()
            message = invMessage[0].getResponse()
            res_info = self.helpers.analyzeResponse(message)
            send_res = message.tostring()
            self._text_editor.setText(send_res)
        except:
            print('Failed to add data to CRH tab.')

    #
    # Implementation of event action
    #
    def actionPerformed(self, actionEvent):

        # onclick add button of extract from regex group
        if actionEvent.getSource() is self._add_btn:
            start, end = self._text_editor.getSelectionBounds()
            value = None
            regex = None
            item = self._dropdown.getSelectedItem()
            param = self._jTextIn_param.getText()

            if len(param) is 0:
                self._param_error.setVisible(True)
                return
            self._param_error.setVisible(False)
            is_selected = self._is_use_regex.isSelected()
            if is_selected:
                start = None
                end = None
                regex = self._jTextIn_regex.getText()
                if len(regex) is 0:
                    self._regex_error.setVisible(True)
                    return

                req = self._text_editor.getText()
                try:
                    pattern = re.compile(regex)
                    match = pattern.search(req)
                    value = match.group(1) if match else None
                    if value is None:
                        raise IndexError
                except IndexError:
                    self._regex_error.setVisible(True)
                    return
                self._regex_error.setVisible(False)

            data = [
                item,
                param,
                regex,
                start,
                end,
            ]
            self.target_table_model.addRow(data)

            with open("target.json", "r+") as f:
                try:
                    json_data = json.load(f)
                except ValueError:
                    json_data = dict()
                if is_selected:
                    data = {
                        param: [
                            item,
                            regex,
                        ]
                    }
                else:
                    data = {
                        param: [
                            item,
                            start,
                            end,
                        ]
                    }
                json_data.update(data)
                self.write_file(f, json.dumps(json_data))

        # onclick remove button of extract from regex group
        if actionEvent.getSource() is self._remove_btn:
            rowno = self.target_table.getSelectedRow()
            if rowno != -1:
                column_model = self.target_table.getColumnModel()
                param_name = self.target_table_model.getValueAt(rowno, 1)
                start = self.target_table_model.getValueAt(rowno, 3)

                self.target_table_model.removeRow(rowno)
                with open("target.json", 'r+') as f:
                    try:
                        json_data = json.load(f)
                    except ValueError:
                        json_data = dict()

                    for key, value in json_data.items():
                        if value[1] == start and key == param_name:
                            try:
                                del json_data[key]
                            except IndexError:
                                print('Error: {0}: No such json key.'.format(
                                    key))
                    self.write_file(f, json.dumps(json_data))

        # onclick load button of payload sets
        if actionEvent.getSource() is self._file_load_btn:
            #clear table
            self.remove_all(self.file_table_model)
            self.current_column_id = 0

            target_param = self._file_param_text.getText()
            item = self._file_dropdown.getSelectedItem()

            if len(target_param) == 0:
                self._error_message.setVisible(True)
                return
            self._error_message.setVisible(False)

            chooser = JFileChooser()
            chooser.showOpenDialog(actionEvent.getSource())
            file_path = chooser.getSelectedFile().getAbsolutePath()
            with open(file_path, 'r') as f:
                while True:
                    line = f.readline().strip()
                    if not line:
                        break
                    data = [
                        item,
                        target_param,
                        line,
                    ]
                    self.file_table_model.addRow(data)

            with open('target.json', 'r+') as f:
                try:
                    json_data = json.load(f)
                except ValueError:
                    json_data = dict()

                json_data.update({target_param: [
                    item,
                    'Set payload',
                ]})
                self.write_file(f, json.dumps(json_data))

        # onclick clear button of payload sets
        if actionEvent.getSource() is self._file_clear_btn:
            self.remove_all(self.file_table_model)

            self.current_column_id = 0

            with open("target.json", 'r+') as f:
                try:
                    json_data = json.load(f)
                except:
                    json_data = dict()

                for key, value in json_data.items():
                    if isinstance(value[1], unicode):
                        if value[1].encode('utf-8') == 'Set payload':
                            try:
                                del json_data[key]
                            except IndexError:
                                print('Error: {0}: No such json key.'.format(
                                    key))
                self.write_file(f, json.dumps(json_data))

    #
    # Implementaion of ISessionHandlingAction
    #
    def getActionName(self):
        return "custom request handler"

    def performAction(self, current_request, macro_items):

        if len(macro_items) == 0:
            return

        # extract the response headers
        final_response = macro_items[len(macro_items) - 1].getResponse()
        if final_response is None:
            return

        req = self.helpers.analyzeRequest(current_request)

        try:
            with open('target.json', 'r') as f:
                read_data = f.read()
                self.read_data = json.loads(read_data)
        except ValueError:
            sys.stderr.write('Error: json.loads()')
            return

        for key, value in self.read_data.items():
            if value[0] == 'JSON':
                self.set_json_parameter(current_request, final_response, key,
                                        value)
            elif value[0] == 'Header':
                self.set_header(current_request, final_response, key, value)

    def set_json_parameter(self, current_request, final_response, key, value):
        req = self.helpers.analyzeRequest(current_request)

        if IRequestInfo.CONTENT_TYPE_JSON != req.getContentType():
            return False

        body = current_request.getRequest()[req.getBodyOffset():].tostring()
        json_data = json.loads(body, object_pairs_hook=collections.OrderedDict)

        target_keys = filter(lambda x: x == key, json_data.keys())
        if not target_keys:
            return

        req_data = json_data
        column_model = self.file_table.getColumnModel()
        row_count = self.file_table_model.getRowCount()
        for key in target_keys:
            if value[-1] == 'Set payload':
                if row_count > self.current_column_id:
                    req_value = self.file_table_model.getValueAt(
                        self.current_column_id, 2)
                    self.current_column_id += 1
            else:
                # No selected regex
                if len(value) > 2:
                    start, end = value[1:]
                    req_value = final_response[start:end].tostring()
                else:
                    regex = value[1]
                    match = re.search(regex, final_response.tostring())
                    req_value = match.group(1) if match else None

            req_data[key] = req_value

        req = current_request.getRequest()
        json_data_start = self.helpers.indexOf(req, bytearray(body), False, 0,
                                               len(req))

        # glue together header + customized json of request
        current_request.setRequest(
            req[0:json_data_start] +
            self.helpers.stringToBytes(json.dumps(req_data)))

    def set_header(self, current_request, final_response, key, value):
        req = self.helpers.analyzeRequest(current_request)
        headers = req.getHeaders()
        target_keys = []
        for header in headers:
            if header.startswith(key):
                target_keys += [key]

        if not target_keys:
            return

        column_model = self.file_table.getColumnModel()
        row_count = self.file_table_model.getRowCount()
        req = current_request.getRequest()

        for key in target_keys:
            if value[-1] == 'Set payload':
                if row_count > self.current_column_id:
                    req_value = self.file_table_model.getValueAt(
                        self.current_column_id, 2)
                    self.current_column_id += 1
            else:
                # No selected regex
                if len(value) > 2:
                    start, end = value[1:]
                    req_value = final_response[start:end].tostring()
                else:
                    regex = value[1]
                    match = re.search(regex, final_response.string())
                    req_value = match.group(1) if match else None

            key_start = self.helpers.indexOf(req,
                                             bytearray(key.encode('utf-8')),
                                             False, 0, len(req))
            key_end = self.helpers.indexOf(req, bytearray('\r\n'), False,
                                           key_start, len(req))

            keylen = len(key)

        # glue together first line + customized hedaer + rest of request
        current_request.setRequest(
            req[0:key_start] +
            self.helpers.stringToBytes("%s: %s" %
                                       (key.encode('utf-8'), req_value)) +
            req[key_end:])

    #
    # Implementation of function for Remove all for specific table data
    #
    def remove_all(self, model):
        count = model.getRowCount()
        for i in xrange(count):
            model.removeRow(0)

    #
    # Implementaion of function for write data for specific file
    #
    def write_file(self, f, data):
        f.seek(0)
        f.write(data)
        f.truncate()
        return