def __init__(self, cattr): self.attr = cattr self.cbox = JColorChooser(self.attr.color) self.sym_panel = EditSymbolAttr(cattr.sym_prop) self.thickness_field = JTextField(str(cattr.thickness),2) self.draw_symbol_box = JCheckBox("Draw Symbol?",cattr.draw_symbol) self.dps_field = JTextField(str(self.attr.data_per_symbol),2) self.dash_box = JComboBox(CurveProps.DASH_TYPES.keys()) self.dash_box.setSelectedItem(self.attr.dash_type) self.dash_box.setBorder(BorderFactory.createTitledBorder("Dash type: (Only JDK2 & Slow!)")) tpanelx = JPanel() tpanelx.add(self.thickness_field) tpanelx.setBorder(BorderFactory.createTitledBorder("curve thickness (integer)")) tpanely = JPanel() tpanely.add(self.dps_field) tpanely.setBorder(BorderFactory.createTitledBorder("data per symbol(integer)")) tpanel = JPanel();tpanel.setLayout(GridLayout(2,2)); tpanel.add(self.draw_symbol_box); tpanel.add(tpanelx); tpanel.add(tpanely); tpanel.add(self.dash_box); panel1 = JPanel() panel1.setLayout(BorderLayout()) panel1.add(self.cbox,BorderLayout.CENTER) panel1.add(tpanel, BorderLayout.SOUTH) panel2 = JPanel() panel2.setLayout(BorderLayout()) panel2.add(self.sym_panel,BorderLayout.CENTER) tp1 = JTabbedPane() tp1.addTab("Curve Attributes",panel1) tp1.addTab("Symbol Attributes",panel2) tp1.setSelectedComponent(panel1) self.setLayout(BorderLayout()) self.add(tp1,BorderLayout.CENTER)
def createEditorComponent(self, properties): p = JPanel(GridBagLayout()) p.setBorder(BorderFactory.createEmptyBorder(3, 3, 3, 3)) gbc = GridBagConstraints() gbc.gridx = 0 gbc.gridy = 0 gbc.weightx = 0.0 gbc.weighty = 0.0 gbc.fill = GridBagConstraints.HORIZONTAL gbc.insets = Insets(3, 3, 3, 3) p.add(JLabel("Prompt:"), gbc) gbc.gridx = 1 editor = NodePropertiesDialog.createTextArea(properties, self.PROMPT) p.add(editor, gbc) gbc.gridx, gbc.gridy = 1, 0 p.add( NodePropertiesDialog.createCheckBox(properties, self.WAIT, "Wait until done"), gbc) jtp = JTabbedPane() jtp.addTab("Output", p) return jtp
def registerExtenderCallbacks(self, callbacks): # keep a reference to our callbacks object self._callbacks = callbacks # obtain an extension helpers object self._helpers = callbacks.getHelpers() # set our extension name callbacks.setExtensionName("sensitive") # create the log and a lock on which to synchronize when adding log entries self._log = ArrayList() self._lock = Lock() self._urls = [] # main split pane self._splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT) # table of log entries logTable = Table(self) scrollPane = JScrollPane(logTable) self._splitpane.setLeftComponent(scrollPane) # tabs with request/response viewers tabs = JTabbedPane() self._requestViewer = callbacks.createMessageEditor(self, False) self._responseViewer = callbacks.createMessageEditor(self, False) tabs.addTab("Request", self._requestViewer.getComponent()) tabs.addTab("Response", self._responseViewer.getComponent()) self._splitpane.setRightComponent(tabs) # customize our UI components callbacks.customizeUiComponent(self._splitpane) callbacks.customizeUiComponent(logTable) callbacks.customizeUiComponent(scrollPane) callbacks.customizeUiComponent(tabs) # add the custom tab to Burp's UI callbacks.addSuiteTab(self) # register ourselves as an HTTP listener callbacks.registerHttpListener(self) return
class OptionsPanel(JPanel): def __init__(self,view): self.view=view self.layout=BorderLayout() self.parameters=ParametersPanel(self.view) self.add(self.parameters,BorderLayout.NORTH) self.tabs=JTabbedPane(stateChanged=self.changed) self.bar_tab=BarTab(self) self.line_tab=LineTab(self) self.tabs.addTab('Bar',self.bar_tab) self.tabs.addTab('Line',self.line_tab) self.add(self.tabs) setattr(self, 'global', GlobalPanel(self)) self.add(getattr(self, 'global'), BorderLayout.SOUTH) def get_graph_type(self): if self.tabs.selectedIndex==0: return 'bar' elif self.tabs.selectedIndex==1: return 'line' else: return None def update(self): self.parameters.update(self.view.stats.params,self.view.stats.options,self.view.stats.defaults) def changed(self,event): self.view.graph.update()
def addTabs( self, container ) : head = 'Row,Col,Cell'.split( ',' ) junk = 'False,True'.split( ',' ) data = [ [ 0, 1 ], [ 0, 1 ] ] info = JTable( # Used to get default attributes data, head, selectionMode = LSM.SINGLE_SELECTION ) bTable = JTable( booleanTM( self.settings( info ), head ) ) tab1 = JPanel() tab1.add( JScrollPane( bTable ) ) info = JTable( data, head, selectionMode = LSM.SINGLE_INTERVAL_SELECTION ) bTable = JTable( booleanTM( self.settings( info ), head ) ) tab2 = JPanel() tab2.add( JScrollPane( bTable ) ) info = JTable( data, head, selectionMode = LSM.MULTIPLE_INTERVAL_SELECTION ) bTable = JTable( booleanTM( self.settings( info ), head ) ) tab3 = JPanel() tab3.add( JScrollPane( bTable ) ) tabs = JTabbedPane() tabs.addTab( 'Single' , tab1 ) tabs.addTab( 'One Group' , tab2 ) tabs.addTab( 'Multi-Group', tab3 ) container.add( tabs )
def initGui(self): #~ if DEBUG: #~ import pdb; #~ pdb.set_trace() tabPane = JTabbedPane(JTabbedPane.TOP) CreditsText = "<html># Burp Custom Deserializer<br/># Copyright (c) 2016, Marco Tinari<br/>#<br/># This program is free software: you can redistribute it and/or modify<br/># it under the terms of the GNU General Public License as published by<br/># the Free Software Foundation, either version 3 of the License, or<br/># (at your option) any later version.<br/>#<br/># This program is distributed in the hope that it will be useful,<br/># but WITHOUT ANY WARRANTY; without even the implied warranty of<br/># MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the<br/># GNU General Public License for more details.<br/>#<br/># You should have received a copy of the GNU General Public License<br/># along with this program. If not, see <http://www.gnu.org/licenses/>.)<br/></html>" label1 = JLabel("<html>Usage:<br>1 - Select the desired encoding functions<br>2 - Enter the name of the parameter in the input field below and press the Apply button!</html>") label2 = JLabel(CreditsText) panel1 = JPanel() #set layout panel1.setLayout(GridLayout(11,1)) panel2 = JPanel() panel1.add(label1) panel2.add(label2) tabPane.addTab("Configuration", panel1) tabPane.addTab("Credits", panel2) applyButton = JButton('Apply',actionPerformed=self.reloadConf) panel1.add(applyButton, BorderLayout.SOUTH) #define GET/POST/COOKIE radio button self.GETparameterTypeRadioButton = JRadioButton('GET parameter') self.POSTparameterTypeRadioButton = JRadioButton('POST parameter') self.COOKIEparameterTypeRadioButton = JRadioButton('COOKIE parameter') self.POSTparameterTypeRadioButton.setSelected(True) group = ButtonGroup() group.add(self.GETparameterTypeRadioButton) group.add(self.POSTparameterTypeRadioButton) group.add(self.COOKIEparameterTypeRadioButton) self.base64Enabled = JCheckBox("Base64 encode") self.URLEnabled = JCheckBox("URL encode") self.ASCII2HexEnabled = JCheckBox("ASCII to Hex") self.ScannerEnabled = JCheckBox("<html>Enable serialization in Burp Scanner<br>Usage:<br>1.Place unencoded values inside intruder request and define the placeholder positions<br>2.rightclick->Actively scan defined insertion points)</html>") self.IntruderEnabled = JCheckBox("<html>Enable serialization in Burp Intruder<br>Usage:<br>1.Place unencoded values inside intruder request and define the placeholder positions<br>2.Start the attack</html>") self.parameterName = JTextField("Parameter name goes here...",60) #set the tooltips self.parameterName.setToolTipText("Fill in the parameter name and apply") self.base64Enabled.setToolTipText("Enable base64 encoding/decoding") self.ASCII2HexEnabled.setToolTipText("Enable ASCII 2 Hex encoding/decoding") self.URLEnabled.setToolTipText("Enable URL encoding/decoding") self.IntruderEnabled.setToolTipText("Check this if You want the extension to intercept and modify every request made by the Burp Intruder containing the selected paramter") self.ScannerEnabled.setToolTipText("Check this if You want the extension to intercept and modify every request made by the Burp Scanner containing the selected paramter") #add checkboxes to the panel panel1.add(self.parameterName) panel1.add(self.POSTparameterTypeRadioButton) panel1.add(self.GETparameterTypeRadioButton) panel1.add(self.COOKIEparameterTypeRadioButton) panel1.add(self.base64Enabled) panel1.add(self.URLEnabled) panel1.add(self.ASCII2HexEnabled) panel1.add(self.IntruderEnabled) panel1.add(self.ScannerEnabled) #assign tabPane self.tab = tabPane
def build_tabbed_panel(self): ''' Build panel with tabs for each of the settings editable sections. ''' tabbed_pane = JTabbedPane() tab_titles = ["General", "Keystrokes", "Languages", "Projects"] for title in tab_titles: panel = self.build_settings_panel(title.lower()) tabbed_pane.addTab(title, panel) return tabbed_pane
def registerExtenderCallbacks(self, callbacks): # keep a reference to our callbacks object self._callbacks = callbacks # obtain an extension helpers object self._helpers = callbacks.getHelpers() # set our extension name callbacks.setExtensionName("CrownJewelFinder") # create the log and a lock on which to synchronize when adding log entries self._log = ArrayList() self._lock = Lock() # main split pane self._splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT) # tabs with request/response viewers tabs = JTabbedPane() self._requestViewer = callbacks.createMessageEditor(self, False) self._responseViewer = callbacks.createMessageEditor(self, False) tabs.addTab("Request", self._requestViewer.getComponent()) tabs.addTab("Response", self._responseViewer.getComponent()) self._splitpane.setRightComponent(tabs) # table of log entries logTable = Table(self) scrollPane = JScrollPane(logTable) self._splitpane.setLeftComponent(scrollPane) # customize our UI components callbacks.customizeUiComponent(self._splitpane) callbacks.customizeUiComponent(logTable) callbacks.customizeUiComponent(scrollPane) callbacks.customizeUiComponent(tabs) #Compile RegEx Patterns regex = "[A-Z0-9]{5,20}" self.myre = re.compile(regex, re.DOTALL) # restore burp state self.file = '' #file = java.io.File('E:/Projects/CPF/Burp-States-Dump/Iteration3-1June2015/172.24.101.42/2015.06.01_08.17.burp') #print file.__class__ #print file.exists() #callbacks.restoreState(file) #get Request/Response from history #reqres = callbacks.getProxyHistory() #print len(reqres) #self.RetrievInterestingRequests(callbacks, reqres) # add the custom tab to Burp's UI callbacks.addSuiteTab(self) self.doInterestingThings() #self.fileInput() return
def build_tabbed_panel(self): ''' Build panel with tabs for each of the settings editable sections. ''' tabbed_pane = JTabbedPane() tab_titles = ["General", "Appearance", "Keystrokes", "Languages", "Projects"] for title in tab_titles: panel = self.build_settings_panel(title.lower()) tabbed_pane.addTab(title, panel) return tabbed_pane
def getUiComponent(self): """Burp uses this method to obtain the component that should be used as the contents of the custom tab when it is displayed. Returns a awt.Component. """ # GUI happens here from javax.swing import (JPanel, JSplitPane, JList, JTextPane, JScrollPane, ListSelectionModel, JLabel, JTabbedPane, JEditorPane) from java.awt import BorderLayout panel = JPanel(BorderLayout()) # create a list and then JList out of it. colors = [ "red", "orange", "yellow", "green", "cyan", "blue", "pink", "magenta", "gray", "zzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzz" ] def listSelect(event): """Add the selected index to the label. Called twice when selecting the list item by mouse. So we need to use getValueIsAdjusting inside. """ if not event.getValueIsAdjusting(): doc1.insertString(0, colors[list1.selectedIndex] + "-", None) # create a list and assign the valueChanged list1 = JList(colors, valueChanged=listSelect) list1.selectionMode = ListSelectionModel.SINGLE_SELECTION # create a StyledDocument. from javax.swing.text import DefaultStyledDocument doc1 = DefaultStyledDocument() # create a JTextPane from doc1 tab1 = JTextPane(doc1) # create a JEditorPane for tab 2 tab2 = JEditorPane("https://example.net") tab2.editable = False # create the tabbedpane tabs = JTabbedPane() tabs.addTab("Tab 1", tab1) tabs.addTab("Tab 2", tab2) # create splitpane - horizontal split spl = JSplitPane(JSplitPane.HORIZONTAL_SPLIT, JScrollPane(list1), tabs) panel.add(spl) return panel
def registerExtenderCallbacks(self, this_callbacks): # stolen from activescan++ global callbacks, helpers callbacks = this_callbacks helpers = callbacks.getHelpers() # keep a reference to our callbacks object self._callbacks = this_callbacks # obtain an extension helpers object self._helpers = this_callbacks.getHelpers() # set our extension name callbacks.setExtensionName("ParamScraper") # create the log and a lock on which to synchronize when adding log entries self._log = ArrayList() self._lock = Lock() # main split pane self._splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT) # table of log entries logTable = Table(self, self._helpers) scrollPane = JScrollPane(logTable) self._splitpane.setLeftComponent(scrollPane) # tabs with request/response viewers tabs = JTabbedPane() self._requestViewer = callbacks.createMessageEditor(self, False) self._responseViewer = callbacks.createMessageEditor(self, False) tabs.addTab("Request With Scraped Parameters", self._requestViewer.getComponent()) tabs.addTab("Response", self._responseViewer.getComponent()) self._splitpane.setRightComponent(tabs) # customize our UI components callbacks.customizeUiComponent(self._splitpane) callbacks.customizeUiComponent(logTable) callbacks.customizeUiComponent(scrollPane) callbacks.customizeUiComponent(tabs) # add the custom tab to Burp's UI callbacks.addSuiteTab(self) # register ourself as a context menu...thing callbacks.registerContextMenuFactory(self) return
def createRequestTabs(self, requestResponse): requestTabs = JTabbedPane() requestViewer = self._extender._callbacks.createMessageEditor(self._extender, False) responseViewer = self._extender._callbacks.createMessageEditor(self._extender, False) requestTabs.addTab("Request", requestViewer.getComponent()) requestTabs.addTab("Response", responseViewer.getComponent()) self._extender._callbacks.customizeUiComponent(requestTabs) # TODO: consider adding the results when clicking the tab (lazy instantiation) since it can get slow requestViewer.setMessage(requestResponse.getRequest(), True) if requestResponse.getResponse(): responseViewer.setMessage(requestResponse.getResponse(), False) requestTabs.setSelectedIndex(1) return requestTabs
class FormattingVisitor( NodeVisitor ) : #--------------------------------------------------------------------------- # Name: __init__() # Role: constructor #--------------------------------------------------------------------------- def __init__( self, url ) : self.Tabs = JTabbedPane() self.header = re.compile( '[hH][1-6]$' ) self.h3Text = '' #--------------------------------------------------------------------------- # Name: head() # Role: Invoked when open tag is first seen # Note: node.text() = "the combined text of this element and all its children" #--------------------------------------------------------------------------- def head( self, node, depth ) : name = node.nodeName() if re.match( self.header, name ) : self.h3Text = [ '', node.text() ] [ name[ 1 ] == '3' ] #--------------------------------------------------------------------------- # Name: tail() # Role: Invoked when end tag is seen #--------------------------------------------------------------------------- def tail( self, node, depth ) : name = node.nodeName() if self.h3Text and name == 'table' : node.attr( 'border', '1' ) ePane = JEditorPane( 'text/html', # mime type '<html>' + str( node ), # content editable = 0 ) self.Tabs.addTab( self.h3Text, JScrollPane( ePane ) ) # print 'addTab( "%s" )' % self.h3Text #--------------------------------------------------------------------------- # Name: toString() # Role: Return a multi-line string of the JTabbedPane titles #--------------------------------------------------------------------------- def toString( self ) : tp = self.Tabs return '\n'.join( [ tp.getTitleAt( i ) for i in range( tp.getTabCount() ) ] )
def addTabs(self, container): align = [['Left', Component.LEFT_ALIGNMENT], ['Center', Component.CENTER_ALIGNMENT], ['Right', Component.RIGHT_ALIGNMENT]] names = '1,2,3 being the third number'.split(',') tabs = JTabbedPane() for aName, aConst in align: tab = JPanel() tab.setLayout(BoxLayout(tab, BoxLayout.Y_AXIS)) for name in names: tab.add(JButton(name, alignmentX=aConst)) tabs.addTab(aName, tab) container.add(tabs)
def createRequestTabs(self, requestResponse): requestTabs = JTabbedPane() requestViewer = self._extender._callbacks.createMessageEditor( self._extender, False) responseViewer = self._extender._callbacks.createMessageEditor( self._extender, False) requestTabs.addTab("Request", requestViewer.getComponent()) requestTabs.addTab("Response", responseViewer.getComponent()) self._extender._callbacks.customizeUiComponent(requestTabs) requestViewer.setMessage(requestResponse.getRequest(), True) if requestResponse.getResponse(): responseViewer.setMessage(requestResponse.getResponse(), False) requestTabs.setSelectedIndex(1) return requestTabs
def registerExtenderCallbacks(self, callbacks): global statement,con self._callbacks = callbacks self._helpers = callbacks.getHelpers() callbacks.setExtensionName("SQLite Logger") # select sqlite jdbc jar file c = classPathHacker() c.addFile("C:\\sqlite-jdbc-3.8.11.2.jar") # database filename. jdbc_url = "jdbc:sqlite:database" + str(datetime.date.today()) + ".db" driver = "org.sqlite.JDBC" Class.forName(driver).newInstance() con = DriverManager.getConnection(jdbc_url) # create table self.sql = "CREATE TABLE if not exists log(host text,path text,method text,request text,response text,time text);" statement = con.prepareStatement(self.sql) statement.executeUpdate() self._log = ArrayList() self._lock = Lock() self._splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT) logTable = Table(self) scrollPane = JScrollPane(logTable) self._splitpane.setLeftComponent(scrollPane) tabs = JTabbedPane() self._requestViewer = callbacks.createMessageEditor(self, False) self._responseViewer = callbacks.createMessageEditor(self, False) tabs.addTab("Request", self._requestViewer.getComponent()) tabs.addTab("Response", self._responseViewer.getComponent()) self._splitpane.setRightComponent(tabs) callbacks.customizeUiComponent(self._splitpane) callbacks.customizeUiComponent(logTable) callbacks.customizeUiComponent(scrollPane) callbacks.customizeUiComponent(tabs) callbacks.addSuiteTab(self) callbacks.registerHttpListener(self) return
def createRequestTabs(self, requestResponse): requestTabs = JTabbedPane() requestViewer = self._extender._callbacks.createMessageEditor( self._extender, False) responseViewer = self._extender._callbacks.createMessageEditor( self._extender, False) requestTabs.addTab("Request", requestViewer.getComponent()) requestTabs.addTab("Response", responseViewer.getComponent()) self._extender._callbacks.customizeUiComponent(requestTabs) # TODO: consider adding the results when clicking the tab (lazy instantiation) since it can get slow requestViewer.setMessage(requestResponse.getRequest(), True) if requestResponse.getResponse(): responseViewer.setMessage(requestResponse.getResponse(), False) requestTabs.setSelectedIndex(1) return requestTabs
def buildUi(self, state, callbacks): """ Handles the building of the UI components using Swing, a UI library. """ self.callbacks = ToolboxCallbacks(state, callbacks) state.toolboxCallbacks = self.callbacks tabs = JTabbedPane() resultsPane = self.buildResultsPane(state, callbacks) configPane = self.buildConfigPane(state, callbacks) tabs.addTab("Results", resultsPane) tabs.addTab("Config", configPane) return tabs
def addTabs(self, container): tab1 = JPanel() tab1.add(JLabel('The quick brown fox jumped over the lazy dog.')) tab2 = JPanel() for name in 'A,B,C'.split(','): tab2.add(JButton(name)) tab3 = JPanel() tab3.add(JLabel('Now is the time for all good men to come to...')) tabs = JTabbedPane() tabs.addTab('Uno', tab1) tabs.addTab('Dos', tab2) tabs.addTab('Tres', tab3) container.add(tabs)
def registerExtenderCallbacks(self, callbacks): # keep a reference to our callbacks object self._callbacks = callbacks # obtain an extension helpers object self._helpers = callbacks.getHelpers() # set our extension name callbacks.setExtensionName("Reflected XSS Detector") # create the log and a lock on which to synchronize when adding log entries self._log = ArrayList() self._lock = Lock() # main split pane self._splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT) # table of log entries logTable = Table(self) scrollPane = JScrollPane(logTable) self._splitpane.setLeftComponent(scrollPane) logTable.addMouseListener( CMouseListener(self) ) # tabs with request/response viewers tabs = JTabbedPane() self._requestViewer = callbacks.createMessageEditor(self, False) self._responseViewer = callbacks.createMessageEditor(self, False) tabs.addTab("Response", self._responseViewer.getComponent()) tabs.addTab("Request", self._requestViewer.getComponent()) self._splitpane.setRightComponent(tabs) # customize our UI components callbacks.customizeUiComponent(self._splitpane) callbacks.customizeUiComponent(logTable) callbacks.customizeUiComponent(scrollPane) callbacks.customizeUiComponent(tabs) # add the custom tab to Burp's UI callbacks.addSuiteTab(self) # register ourselves as an HTTP listener callbacks.registerHttpListener(self) return
def registerExtenderCallbacks(self, callbacks): self._callbacks = callbacks self._helpers = callbacks.getHelpers() #self.context = None # main split pane self._splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT) self._splitpane2 = JSplitPane(JSplitPane.HORIZONTAL_SPLIT) # Table of RequestLists requestTable = TableOne(self) scrollPane = JScrollPane(requestTable) self._splitpane.setLeftComponent(scrollPane) # Request List self._reqstack = ArrayList() self._lock = Lock() # tabs with request/response viewers tabs = JTabbedPane() self._requestViewer = callbacks.createMessageEditor(self, False) self._responseViewer = callbacks.createMessageEditor(self, False) tabs.addTab("Request", self._requestViewer.getComponent()) tabs.addTab("Response", self._responseViewer.getComponent()) self._splitpane.setRightComponent(tabs) # customize our UI components callbacks.customizeUiComponent(self._splitpane) callbacks.customizeUiComponent(requestTable) callbacks.customizeUiComponent(scrollPane) callbacks.customizeUiComponent(tabs) # Extention Name and Info callbacks.setExtensionName("ReqSquared") callbacks.registerContextMenuFactory(self) # Initialize tab callbacks.addSuiteTab(self) # IntruderPayloadGeneratorFactory #callbacks.registerIntruderPayloadGeneratorFactory(self) return
def getUiComponent(self): """Burp uses this method to obtain the component that should be used as the contents of the custom tab when it is displayed. Returns a awt.Component. """ # GUI happens here from javax.swing import (JPanel, JSplitPane, JList, JScrollPane, ListSelectionModel, JLabel, JTabbedPane) from java.awt import BorderLayout panel = JPanel(BorderLayout()) # create a list and then JList out of it. colors = [ "red", "orange", "yellow", "green", "cyan", "blue", "pink", "magenta", "gray", "zzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzz" ] def listSelect(event): """Add the selected index to the label. Called twice when selecting the list item by mouse. So we need to use getValueIsAdjusting inside. """ if not event.getValueIsAdjusting(): label1.text += "-" + colors[list1.selectedIndex] # create a list and assign the valueChanged list1 = JList(colors, valueChanged=listSelect) list1.selectionMode = ListSelectionModel.SINGLE_SELECTION # create a JTabbedPane tabs = JTabbedPane() # add labels to it label1 = JLabel() label2 = JLabel() tabs.addTab("Tab 1", label1) tabs.addTab("Tab 2", label2) # create splitpane - horizontal split spl = JSplitPane(JSplitPane.HORIZONTAL_SPLIT, JScrollPane(list1), tabs) panel.add(spl) return panel
class SwingExample: def __init__(self): self.mainFrame = None self.mainTabbedPane = JTabbedPane() def start(self): self.mainFrame = JFrame("SwingTest") self.mainFrame.setSize(800, 600) self.mainFrame.setLocationRelativeTo(None) self.mainFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE) self.mainFrame.add(self.mainTabbedPane) self.mainFrame.setVisible(True) def addToTabbedPane(self, tabName, component): self.mainTabbedPane.addTab(tabName, component) def main(self): self.addToTabbedPane("Beautify", BeautifierPanel()) self.addToTabbedPane("Options", BeautifierOptionsPanel(None)) self.start()
def __init__(self, callbacks): self.callbacks = callbacks noTabs = 1 # load tabs from burp settings (if previously saved by cacheTabs()) try: serialized = self.callbacks.loadExtensionSetting(BurpExtender.name) if serialized: # deserialize cachedTabs cachedTabs = pickle.loads(serialized) noTabs = len(cachedTabs) except: print pformat(sys.exc_info()) # the main container jTabbedPane = JTabbedPane() if serialized: for i in range(noTabs): jTabTitle = JTabTitle(self, cachedTabs[i].jTabTitle) jTabPanel = JTabPanel(self) jTabPanel.jFileName.setText(cachedTabs[i].jFileName) jTabPanel.jVarsPane.setText(cachedTabs[i].jVarsPane) jTabPanel.jScriptPane.setText(cachedTabs[i].jScriptPane) jTabbedPane.addTab("", JLabel("")) jTabbedPane.setTabComponentAt(i, jTabTitle) jTabbedPane.setComponentAt(i, jTabPanel) else: # add the first tab jTabTitle = JTabTitle(self, Strings.jTabTitle_default_name) jTabPanel = JTabPanel(self) # try to load the example try: # read from file examplePath = FileSystems.getDefault().getPath( os.getcwd() + "/examples/Simple-CSRF.py") (vars, script) = FileUtils.read(examplePath) # load the default text except: print pformat(sys.exc_info()) vars = Strings.jVarsPane_header script = Strings.jScriptPane_header jTabPanel.jVarsPane.setText(vars) jTabPanel.jScriptPane.setText(script) jTabbedPane.addTab("", JLabel("")) jTabbedPane.setTabComponentAt(0, jTabTitle) jTabbedPane.setComponentAt(0, jTabPanel) # add the "..." tab jTabbedPane.addTab("", JLabel("")) jTabbedPane.setTabComponentAt(noTabs, JNewTabTitle(self)) jTabbedPane.setComponentAt(noTabs, JPanel()) self.jTabbedPane = jTabbedPane
def registerExtenderCallbacks(self, callbacks): # keep a reference to our callbacks object self._callbacks = callbacks # obtain an extension helpers object self._helpers = callbacks.getHelpers() #setup the extension callbacks.setExtensionName('ExampleExtension') # main split pane self._splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT) # table of log entries logTable = Table(self) scrollPane = JScrollPane(logTable) self._splitpane.setLeftComponent(scrollPane) # Setup the tab for the results tabs = JTabbedPane() linkResults_tab = self.set_linkResults_tab(functionality_name, test_name) self._resultsViewer = callbacks.createMessageEditor(self, False) tabs.addTab("Results", linkResults_tab) self._splitpane.setRightComponent(tabs) stdout = PrintWriter(callbacks.getStdout(), True) stderr = PrintWriter(callbacks.getStderr(), True) #callbacks.registerScannerCheck(self) callbacks.registerContextMenuFactory(self) # customize our UI components callbacks.customizeUiComponent(self._splitpane) callbacks.customizeUiComponent(logTable) callbacks.customizeUiComponent(scrollPane) callbacks.customizeUiComponent(tabs) # add the custom tab to Burp's UI callbacks.addSuiteTab(self) return
def buildMessageViewer(self, state, callbacks): """ Builds the panel that allows users to view requests on the results page. Args: state: the state object. callbacks: the burp callbacks object. """ tabs = JTabbedPane() original = JSplitPane() original.setDividerLocation(1000) modified = JSplitPane() modified.setDividerLocation(1000) originalRequestEditor = MessageEditorController(state, "original") repeatedRequestEditor = MessageEditorController(state, "repeated") state.originalRequestViewer = callbacks.createMessageEditor( originalRequestEditor, False) state.originalResponseViewer = callbacks.createMessageEditor( originalRequestEditor, False) state.repeatedRequestViewer = callbacks.createMessageEditor( repeatedRequestEditor, False) state.repeatedResponseViewer = callbacks.createMessageEditor( repeatedRequestEditor, False) original.setLeftComponent(state.originalRequestViewer.getComponent()) original.setRightComponent(state.originalResponseViewer.getComponent()) modified.setLeftComponent(state.repeatedRequestViewer.getComponent()) modified.setRightComponent(state.repeatedResponseViewer.getComponent()) tabs.addTab("Original", original) tabs.addTab("Modified", modified) return tabs
def registerExtenderCallbacks(self, callbacks): # set our extension name self._callbacks = callbacks self.ATTRIBUTE_QUOTES = "(\".*\")|(\'.*\')" callbacks.setExtensionName("Rexsser") # obtain our output stream self._stdout = PrintWriter(callbacks.getStdout(), True) self._helpers = callbacks.getHelpers() # register ourselves as an HTTP listener self._log = ArrayList() self._lock = Lock() # main split pane self._splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT) # table of log entries logTable = Table(self) scrollPane = JScrollPane(logTable) self._splitpane.setLeftComponent(scrollPane) # tabs with request/response viewers tabs = JTabbedPane() self._requestViewer = callbacks.createMessageEditor(self, False) self._responseViewer = callbacks.createMessageEditor(self, False) tabs.addTab("Request", self._requestViewer.getComponent()) tabs.addTab("Response", self._responseViewer.getComponent()) self._splitpane.setRightComponent(tabs) # customize our UI components callbacks.customizeUiComponent(self._splitpane) callbacks.customizeUiComponent(logTable) callbacks.customizeUiComponent(scrollPane) callbacks.customizeUiComponent(tabs) # add the custom tab to Burp's UI callbacks.addSuiteTab(self) callbacks.registerHttpListener(self) return
def __init__(self, interface): self.interface = interface self.frame = JFrame("Python Window") tabs = JTabbedPane() # Create Interactive Pane interactive_pane = JPanel(BorderLayout()) scrollpane = JScrollPane() inputPanel = JPanel() inputPanel.layout = GridLayout(1, 1) self.check_disabled = LockManager() self.input = InteractiveInput(self.check_disabled, self.runcode) self.input.component.document.addDocumentListener(self) inputPanel.add(self.input.component) self.outputpane = OutputPane() scrollpane.viewport.view = self.outputpane.textpane interactive_pane.add(scrollpane, BorderLayout.CENTER) interactive_pane.add(inputPanel, BorderLayout.PAGE_END) # Create Script Pane script_pane = JPanel(BorderLayout()) scrollpane = JScrollPane() self.script_area = script_area = InputPane() line_numbers = LineNumbering(self.script_area.component) scrollpane.viewport.view = self.script_area.component scrollpane.rowHeaderView = line_numbers.component script_pane.add(scrollpane, BorderLayout.CENTER) tabs.addTab("Interactive", interactive_pane) tabs.addTab("Script", script_pane) self.frame.add(tabs) self.frame.size = 500, 600 self.frame.visible = False self.component = None self.make_menubar() self.history = InputHistory()
def run(self): screenSize = Toolkit.getDefaultToolkit().getScreenSize() frameSize = Dimension( # Initial frame size screenSize.width >> 2, # 1/4 screen width screenSize.height >> 2 # 1/4 screen height ) frame = JFrame('WSAShelp_02', size=frameSize, locationRelativeTo=None, defaultCloseOperation=JFrame.EXIT_ON_CLOSE) #----------------------------------------------------------------------- # Reposition the frame to be in the center of the screen # Note: This is done based upon initial frameSize, not packed() size... #----------------------------------------------------------------------- frame.setLocation((screenSize.width - frameSize.width) >> 1, (screenSize.height - frameSize.height) >> 1) #----------------------------------------------------------------------- # Create & Populate the JTabbedPane #----------------------------------------------------------------------- objs = [('Help', Help), ('AdminApp', AdminApp), ('AdminConfig', AdminConfig), ('AdminControl', AdminControl), ('AdminTask', AdminTask)] tabs = JTabbedPane() for name, obj in objs: tabs.addTab( name, JScrollPane( JTextArea(obj.help().expandtabs(), 20, 90, font=Font('Courier', Font.PLAIN, 12)))) #----------------------------------------------------------------------- # Add the tabbed pane to the frame & show the result #----------------------------------------------------------------------- frame.add(tabs) frame.pack() frame.setVisible(1)
def __init__(self, cattr): self.attr = cattr self.cbox = JColorChooser(self.attr.color) self.sym_panel = EditSymbolAttr(cattr.sym_prop) self.thickness_field = JTextField(str(cattr.thickness), 2) self.draw_symbol_box = JCheckBox("Draw Symbol?", cattr.draw_symbol) self.dps_field = JTextField(str(self.attr.data_per_symbol), 2) self.dash_box = JComboBox(CurveProps.DASH_TYPES.keys()) self.dash_box.setSelectedItem(self.attr.dash_type) self.dash_box.setBorder( BorderFactory.createTitledBorder("Dash type: (Only JDK2 & Slow!)")) tpanelx = JPanel() tpanelx.add(self.thickness_field) tpanelx.setBorder( BorderFactory.createTitledBorder("curve thickness (integer)")) tpanely = JPanel() tpanely.add(self.dps_field) tpanely.setBorder( BorderFactory.createTitledBorder("data per symbol(integer)")) tpanel = JPanel() tpanel.setLayout(GridLayout(2, 2)) tpanel.add(self.draw_symbol_box) tpanel.add(tpanelx) tpanel.add(tpanely) tpanel.add(self.dash_box) panel1 = JPanel() panel1.setLayout(BorderLayout()) panel1.add(self.cbox, BorderLayout.CENTER) panel1.add(tpanel, BorderLayout.SOUTH) panel2 = JPanel() panel2.setLayout(BorderLayout()) panel2.add(self.sym_panel, BorderLayout.CENTER) tp1 = JTabbedPane() tp1.addTab("Curve Attributes", panel1) tp1.addTab("Symbol Attributes", panel2) tp1.setSelectedComponent(panel1) self.setLayout(BorderLayout()) self.add(tp1, BorderLayout.CENTER)
class ProgressTab(ITab): def __init__(self): self._ui_component = JTabbedPane() self._ui_component.addTab('Items', ItemsPanel()) self._ui_component.addTab('Path patterns', PathPatternsPanel()) self._ui_component.addTab('Options', JScrollPane(OptionsPanel())) BurpCallbacks.get_instance().customizeUiComponent(self._ui_component) def getTabCaption(self): return 'Progress' def getUiComponent(self): return self._ui_component
class BurpExtender(IBurpExtender, ITab, IMessageEditorController, IContextMenuFactory, ActionListener, AbstractTableModel, Runnable): # # Implement IBurpExtender # def registerExtenderCallbacks(self, callbacks): # Initialize the global stdout stream global stdout # Keep a reference to our callbacks object self._callbacks = callbacks # Obtain an extension helpers object self._helpers = callbacks.getHelpers() # set our extension name callbacks.setExtensionName("Burpsuite Yara Scanner") # Create the log and a lock on which to synchronize when adding log entries self._log = ArrayList() self._lock = Lock() # main split pane splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT) # table of log entries logTable = Table(self) scrollPane = JScrollPane(logTable) splitpane.setLeftComponent(scrollPane) # Options panel optionsPanel = JPanel() optionsPanel.setLayout(GridBagLayout()) constraints = GridBagConstraints() yara_exe_label = JLabel("Yara Executable Location:") constraints.fill = GridBagConstraints.HORIZONTAL constraints.gridx = 0 constraints.gridy = 0 optionsPanel.add(yara_exe_label, constraints) self._yara_exe_txtField = JTextField(25) constraints.fill = GridBagConstraints.HORIZONTAL constraints.gridx = 1 constraints.gridy = 0 optionsPanel.add(self._yara_exe_txtField, constraints) yara_rules_label = JLabel("Yara Rules File:") constraints.fill = GridBagConstraints.HORIZONTAL constraints.gridx = 0 constraints.gridy = 1 optionsPanel.add(yara_rules_label, constraints) self._yara_rules_files = Vector() self._yara_rules_files.add("< None >") self._yara_rules_fileList = JList(self._yara_rules_files) constraints.fill = GridBagConstraints.HORIZONTAL constraints.gridx = 1 constraints.gridy = 1 optionsPanel.add(self._yara_rules_fileList, constraints) self._yara_rules_select_files_button = JButton("Select Files") self._yara_rules_select_files_button.addActionListener(self) constraints.fill = GridBagConstraints.HORIZONTAL constraints.gridx = 1 constraints.gridy = 2 optionsPanel.add(self._yara_rules_select_files_button, constraints) self._yara_clear_button = JButton("Clear Yara Results Table") self._yara_clear_button.addActionListener(self) constraints.fill = GridBagConstraints.HORIZONTAL constraints.gridx = 1 constraints.gridy = 3 optionsPanel.add(self._yara_clear_button, constraints) # Tabs with request/response viewers viewerTabs = JTabbedPane() self._requestViewer = callbacks.createMessageEditor(self, False) self._responseViewer = callbacks.createMessageEditor(self, False) viewerTabs.addTab("Request", self._requestViewer.getComponent()) viewerTabs.addTab("Response", self._responseViewer.getComponent()) splitpane.setRightComponent(viewerTabs) # Tabs for the Yara output and the Options self._mainTabs = JTabbedPane() self._mainTabs.addTab("Yara Output", splitpane) self._mainTabs.addTab("Options", optionsPanel) # customize our UI components callbacks.customizeUiComponent(splitpane) callbacks.customizeUiComponent(logTable) callbacks.customizeUiComponent(scrollPane) callbacks.customizeUiComponent(viewerTabs) callbacks.customizeUiComponent(self._mainTabs) # add the custom tab to Burp's UI callbacks.addSuiteTab(self) # add ourselves as a context menu factory callbacks.registerContextMenuFactory(self) # Custom Menu Item self.menuItem = JMenuItem("Scan with Yara") self.menuItem.addActionListener(self) # obtain our output stream stdout = PrintWriter(callbacks.getStdout(), True) # Print a startup notification stdout.println("Burpsuite Yara scanner initialized.") # # Implement ITab # def getTabCaption(self): return "Yara" def getUiComponent(self): return self._mainTabs # # Implement IContextMenuFactory # def createMenuItems(self, invocation): if invocation.getInvocationContext() == invocation.CONTEXT_TARGET_SITE_MAP_TREE: self.requestResponses = invocation.getSelectedMessages() return [self.menuItem] else: self.requestResponses = None return None # # Implement Action # def actionPerformed(self, actionEvent): global yara_rules global yara_path if actionEvent.getSource() is self.menuItem: yara_path = self._yara_exe_txtField.getText() yara_rules = self._yara_rules_files t = Thread(self) t.start() elif actionEvent.getSource() is self._yara_clear_button: # Delete the LogEntry objects from the log row = self._log.size() self._lock.acquire() self._log.clear() # Update the Table self.fireTableRowsDeleted(0, row) # Clear data regarding any selected LogEntry objects from the request / response viewers self._requestViewer.setMessage([], True) self._responseViewer.setMessage([], False) self._currentlyDisplayedItem = None self._lock.release() elif actionEvent.getSource() is self._yara_rules_select_files_button: fileChooser = JFileChooser() yarFilter = FileNameExtensionFilter("Yara Rules", ["yar"]) fileChooser.addChoosableFileFilter(yarFilter) fileChooser.setFileFilter(yarFilter) fileChooser.setMultiSelectionEnabled(True) fileChooser.setFileSelectionMode(JFileChooser.FILES_ONLY) ret = fileChooser.showOpenDialog(None) if ret == JFileChooser.APPROVE_OPTION: self._yara_rules_files.clear() for file in fileChooser.getSelectedFiles(): self._yara_rules_files.add(file.getPath()) self._yara_rules_fileList.setListData(self._yara_rules_files) else: stdout.println("Unknown Event Received.") # # Implement Runnable # def run(self): self.yaraScan() # # Extend AbstractTableModel # def getRowCount(self): try: return self._log.size() except: return 0 def getColumnCount(self): return 2 def getColumnName(self, columnIndex): if columnIndex == 0: return "Rule Name" if columnIndex == 1: return "URL" return "" def getValueAt(self, rowIndex, columnIndex): logEntry = self._log.get(rowIndex) if columnIndex == 0: return logEntry._ruleName if columnIndex == 1: return logEntry._url.toString() return "" # # Implement IMessageEditorController # this allows our request/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() # # Implement the Yara scanning logic # def yaraScan(self): # If stdout has not yet been initialized, punt. if stdout is None: return # If the location of the yara executable and rules files are NULL, punt. if yara_rules is None or yara_path is None or yara_rules.size() == 0 or yara_rules.contains("< None >") or len(yara_path) == 0: JOptionPane.showMessageDialog(None, "Error: Please specify the path to the yara executable and rules file in " "the options tab.") return # If iRequestResponses is None, punt. if self.requestResponses is None: JOptionPane.showMessageDialog(None, "Error: No Request/Responses were selected.") return else: stdout.println("Processing %d item(s)." % len(self.requestResponses)) # Get the OS temp folder os_name = System.getProperty("os.name").lower() temp_folder = None if "linux" in os_name: temp_folder = "/tmp" elif "windows" in os_name: temp_folder = os.environ.get("TEMP") if temp_folder is None: temp_folder = os.environ.get("TMP") if temp_folder is None: stdout.println("Error: Could not determine TEMP folder location.") return # Keep track of the number of matches. matchCount = 0 # Process the site map selected messages for idx, iRequestResponse in enumerate(self.requestResponses): # Process the request request = iRequestResponse.getRequest() if request is not None: if len(request) > 0: try: # Yara does not support scanning from stdin so we will need to create a temp file and scan it req_filename = os.path.join(temp_folder, "req_" + str(idx) + ".tmp") req_file = open(req_filename, "wb") req_file.write(request) req_file.close() for rules in yara_rules: yara_req_output = subprocess.check_output([yara_path, rules, req_filename]) if yara_req_output is not None and len(yara_req_output) > 0: ruleName = (yara_req_output.split())[0] self._lock.acquire() row = self._log.size() # TODO: Don't add duplicate items to the table self._log.add(LogEntry(ruleName, iRequestResponse, self._helpers.analyzeRequest(iRequestResponse).getUrl())) self.fireTableRowsInserted(row, row) self._lock.release() matchCount += 1 except Exception as e: JOptionPane.showMessageDialog(None, "Error running Yara. Please check your configuration and rules.") return finally: # Remove the temp file if req_file is not None: req_file.close() os.remove(req_filename) # Process the response response = iRequestResponse.getResponse() if response is not None: if len(response) > 0: try: # Yara does not support scanning from stdin so we will need to create a temp file and scan it resp_filename = os.path.join(temp_folder, "resp_" + str(idx) + ".tmp") resp_file = open(resp_filename, "wb") resp_file.write(response) resp_file.close() for rules in yara_rules: yara_resp_output = subprocess.check_output([yara_path, rules, resp_filename]) if yara_resp_output is not None and len(yara_resp_output) > 0: ruleName = (yara_resp_output.split())[0] self._lock.acquire() row = self._log.size() # TODO: Don't add duplicate items to the table self._log.add(LogEntry(ruleName, iRequestResponse, self._helpers.analyzeRequest(iRequestResponse).getUrl())) self.fireTableRowsInserted(row, row) self._lock.release() matchCount += 1 except Exception as e: JOptionPane.showMessageDialog(None, "Error running Yara. Please check your configuration and rules.") return finally: # Remove the temp file if resp_file is not None: resp_file.close() os.remove(resp_filename) # Print a completion notification JOptionPane.showMessageDialog(None, "Yara scanning complete. %d rule(s) matched." % matchCount)
def registerExtenderCallbacks(self, callbacks): # smart xss feature (print conclusion and observation) # mark resulsts # add automatic check pages in the same domain self.tagPayloads = [ "<b>test", "<b onmouseover=test()>test", "<img src=err onerror=test()>", "<script>test</script>" "", "<scr ipt>test</scr ipt>", "<SCRIPT>test;</SCRIPT>", "<scri<script>pt>test;</scr</script>ipt>", "<SCRI<script>PT>test;</SCR</script>IPT>", "<scri<scr<script>ipt>pt>test;</scr</sc</script>ript>ipt>", "<IMG \"\"\"><SCRIPT>test</SCRIPT>\">", "<IMG '''><SCRIPT>test</SCRIPT>'>", "<SCR%00IPT>test</SCR%00IPT>", "<IFRAME SRC='f' onerror=\"test\"></IFRAME>", "<IFRAME SRC='f' onerror='test'></IFRAME>", "<<SCRIPT>test//<</SCRIPT>", "<img src=\"1\" onerror=\"test\">", "<img src='1' onerror='test'", "<STYLE TYPE=\"text/javascript\">test;</STYLE>", "<<SCRIPT>test//<</SCRIPT>" ] self.attributePayloads = [ "\"\"\"><SCRIPT>test", "'''><SCRIPT>test'", "\"><script>test</script>", "\"><script>test</script><\"", "'><script>test</script>", "'><script>test</script><'", "\";test;\"", "';test;'", ";test;", "\";test;//", "\"onmouseover=test ", "onerror=\"test\"", "onerror='test'", "onload=\"test\"", "onload='test'" ] self.xssKey = 'xssme' # keep a reference to our callbacks object self._callbacks = callbacks # obtain an extension helpers object self._helpers = callbacks.getHelpers() # set our extension name callbacks.setExtensionName("XSSor") self.affectedResponses = ArrayList() self._log = ArrayList() self._lock = Lock() # main split pane self._splitpane = JSplitPane(JSplitPane.HORIZONTAL_SPLIT) # table of log entries logTable = Table(self) scrollPane = JScrollPane(logTable) self._splitpane.setLeftComponent(scrollPane) # tabs with request/response viewers tabs = JTabbedPane() self._requestViewer = callbacks.createMessageEditor(self, False) self._responseViewer = callbacks.createMessageEditor(self, False) tabs.addTab("Request", self._requestViewer.getComponent()) tabs.addTab("Response", self._responseViewer.getComponent()) clearAPListBtn = JButton("Clear List", actionPerformed=self.clearAPList) clearAPListBtn.setBounds(10, 85, 120, 30) apListLabel = JLabel('Affected Pages List:') apListLabel.setBounds(10, 10, 140, 30) self.affectedModel = DefaultListModel() self.affectedList = JList(self.affectedModel) self.affectedList.addListSelectionListener(listSelectedChange(self)) scrollAList = JScrollPane(self.affectedList) scrollAList.setVerticalScrollBarPolicy( JScrollPane.VERTICAL_SCROLLBAR_AS_NEEDED) scrollAList.setBounds(150, 10, 550, 200) scrollAList.setBorder(LineBorder(Color.BLACK)) APtabs = JTabbedPane() self._requestAPViewer = callbacks.createMessageEditor(self, False) self._responseAPViewer = callbacks.createMessageEditor(self, False) APtabs.addTab("Request", self._requestAPViewer.getComponent()) APtabs.addTab("Affeced Page Response", self._responseAPViewer.getComponent()) APtabs.setBounds(0, 250, 700, 350) APtabs.setSelectedIndex(1) self.APpnl = JPanel() self.APpnl.setBounds(0, 0, 1000, 1000) self.APpnl.setLayout(None) self.APpnl.add(scrollAList) self.APpnl.add(clearAPListBtn) self.APpnl.add(APtabs) self.APpnl.add(apListLabel) tabs.addTab("Affected Pages", self.APpnl) self.intercept = 0 ## init conf panel startLabel = JLabel("Plugin status:") startLabel.setBounds(10, 10, 140, 30) payloadLabel = JLabel("Basic Payload:") payloadLabel.setBounds(10, 50, 140, 30) self.basicPayload = "<script>alert(1)</script>" self.basicPayloadTxt = JTextArea(self.basicPayload, 5, 30) self.basicPayloadTxt.setBounds(120, 50, 305, 30) self.bruteForceMode = JCheckBox("Brute Force Mode") self.bruteForceMode.setBounds(120, 80, 300, 30) self.bruteForceMode.addItemListener(handleBFModeChange(self)) self.tagPayloadsCheck = JCheckBox("Tag paylods") self.tagPayloadsCheck.setBounds(120, 100, 300, 30) self.tagPayloadsCheck.setSelected(True) self.tagPayloadsCheck.setEnabled(False) self.tagPayloadsCheck.addItemListener(handleBFModeList(self)) self.attributePayloadsCheck = JCheckBox("Attribute payloads") self.attributePayloadsCheck.setBounds(260, 100, 300, 30) self.attributePayloadsCheck.setSelected(True) self.attributePayloadsCheck.setEnabled(False) self.attributePayloadsCheck.addItemListener(handleBFModeList(self)) payloadListLabel = JLabel("Payloads list (for BF mode):") payloadListLabel.setBounds(10, 130, 140, 30) self.payloadsModel = DefaultListModel() self.payloadsList = JList(self.payloadsModel) scrollPayloadsList = JScrollPane(self.payloadsList) scrollPayloadsList.setVerticalScrollBarPolicy( JScrollPane.VERTICAL_SCROLLBAR_AS_NEEDED) scrollPayloadsList.setBounds(120, 170, 300, 200) scrollPayloadsList.setBorder(LineBorder( Color.BLACK)) # add buttons to remove payloads and add for payload in self.tagPayloads: self.payloadsModel.addElement(payload) for payload in self.attributePayloads: self.payloadsModel.addElement(payload) self.startButton = JButton("XSSor is off", actionPerformed=self.startOrStop) self.startButton.setBounds(120, 10, 120, 30) self.startButton.setBackground(Color(255, 100, 91, 255)) consoleTab = JTabbedPane() self.consoleLog = JTextArea("", 5, 30) scrollLog = JScrollPane(self.consoleLog) scrollLog.setVerticalScrollBarPolicy( JScrollPane.VERTICAL_SCROLLBAR_AS_NEEDED) scrollLog.setBounds(120, 170, 550, 200) scrollLog.setBorder(LineBorder(Color.BLACK)) scrollLog.getVerticalScrollBar().addAdjustmentListener( autoScrollListener(self)) consoleTab.addTab("Console", scrollLog) consoleTab.setBounds(0, 400, 500, 200) self.pnl = JPanel() self.pnl.setBounds(0, 0, 1000, 1000) self.pnl.setLayout(None) self.pnl.add(self.startButton) self.pnl.add(startLabel) self.pnl.add(payloadLabel) self.pnl.add(self.basicPayloadTxt) self.pnl.add(self.bruteForceMode) self.pnl.add(payloadListLabel) self.pnl.add(scrollPayloadsList) self.pnl.add(self.attributePayloadsCheck) self.pnl.add(self.tagPayloadsCheck) self.pnl.add(consoleTab) tabs.addTab("Configuration", self.pnl) tabs.setSelectedIndex(3) self._splitpane.setRightComponent(tabs) # customize our UI components callbacks.customizeUiComponent(self._splitpane) callbacks.customizeUiComponent(logTable) callbacks.customizeUiComponent(scrollPane) callbacks.customizeUiComponent(tabs) # add the custom tab to Burp's UI callbacks.addSuiteTab(self) # register ourselves as an HTTP listener callbacks.registerHttpListener(self) self._callbacks.registerContextMenuFactory(self) print "Thank you for installing XSSor v0.1 extension" print "Created by Barak Tawily" print "\nGithub:\nhttps://github.com/Quitten/XSSor" return
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))
def registerExtenderCallbacks(self, callbacks): # Set encoding to utf-8 to avoid some errors reload(sys) sys.setdefaultencoding('utf8') # Keep a reference to callback object and helper object self._callbacks = callbacks self._helpers = callbacks.getHelpers() # Set the extension name that shows in the burp extension menu callbacks.setExtensionName("InjectionScanner") # Create the log and a lock on which to synchronize when adding log entries self._log = ArrayList() self._logLock = Lock() self._httpLock = Lock() # The length of the basis used to fetch abnormal data, default to zero self._basisLen = 0 # 1: {POST. GET}; 2: {urlencoded, json, xml} self._postGet = 'NaN' self._dataType = 'NaN' # Scan list self._simpleList = [ '\'', '\"', '/', '/*', '#', ')', '(', ')\'', '(\'', 'and 1=1', 'and 1=2', 'and 1>2', 'and 12', '+', 'and+12', '/**/and/**/1' ] self._xmlList = ['a', 'b', 'c', 'd', 'e'] # Not setted # Response mutex: True = is blocking; False = free to go # self._mutexR = False # Other classes instance self._dataTable = Guis_DefaultTM() self._logTable = Guis_AbstractTM(self) self._xh = XMLHandler() listeners = Guis_Listeners(self, self._logTable) ''' Setting GUIs ''' # Divide the whole pane two: one upper and one lower pane self._mainSplitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT) self._mainSplitpane.setResizeWeight(0.4) # Initizlize request table dataTable = JTable(self._dataTable) dataScrollPane = JScrollPane(dataTable) dataScrollPane.setPreferredSize(Dimension(0, 125)) self._dataTable.addTableModelListener(listeners) # Initialize log table logTable = Guis_LogTable(self._logTable) logScrollPane = JScrollPane(logTable) logScrollPane.setPreferredSize(Dimension(0, 125)) # Split the upper pane to two panes tableSplitpane = JSplitPane(JSplitPane.HORIZONTAL_SPLIT) tableSplitpane.setResizeWeight(0.5) # Set the data table to the left and log to the right tableSplitpane.setLeftComponent(dataScrollPane) tableSplitpane.setRightComponent(logScrollPane) # Tabs with request/response viewers tabs = JTabbedPane() self._requestViewer = callbacks.createMessageEditor(self, False) self._responseViewer = callbacks.createMessageEditor(self, False) tabs.addTab("Request", self._requestViewer.getComponent()) tabs.addTab("Response", self._responseViewer.getComponent()) # Create buttons that do operation with the test self._basisLabel = JLabel('Basis: ' + str(self._basisLen)) self._levelLabel = JLabel('Level:') self._setBasisButton = JButton('Set Basis') self._hitOnceButton = JButton('Hit Once') self._autoScanButton = JButton('Auto Scan') self._clearLogButton = JButton('Clear Log') self._cancelButton = JButton('Cancel') self._levelSelection = JComboBox() self._levelSelection.addItem('1') self._levelSelection.addItem('2') self._levelSelection.addItem('3') self._hitOnceButton.addActionListener(listeners) self._autoScanButton.addActionListener(listeners) self._clearLogButton.addActionListener(listeners) self._setBasisButton.addActionListener(listeners) self._cancelButton.addActionListener(listeners) self._basisLabel.setPreferredSize(Dimension(100, 20)) # Create bottom pane for holding the buttons buttonPane = JPanel() buttonPane.setLayout(BorderLayout()) centerPane = JPanel() leftPane = JPanel() rightPane = JPanel() leftPane.add(self._basisLabel) centerPane.add(self._setBasisButton) centerPane.add(self._hitOnceButton) centerPane.add(self._autoScanButton) centerPane.add(self._cancelButton) centerPane.add(self._clearLogButton) rightPane.add(self._levelLabel) rightPane.add(self._levelSelection) buttonPane.add(centerPane, BorderLayout.CENTER) buttonPane.add(leftPane, BorderLayout.WEST) buttonPane.add(rightPane, BorderLayout.EAST) # Create and set the bottom panel that holds viewers and buttons utilPane = JPanel() utilPane.setLayout(BorderLayout()) utilPane.add(tabs, BorderLayout.CENTER) utilPane.add(buttonPane, BorderLayout.SOUTH) self._mainSplitpane.setLeftComponent(tableSplitpane) self._mainSplitpane.setRightComponent(utilPane) # Customize UI components callbacks.customizeUiComponent(self._mainSplitpane) callbacks.customizeUiComponent(dataTable) callbacks.customizeUiComponent(dataScrollPane) callbacks.customizeUiComponent(logTable) callbacks.customizeUiComponent(logScrollPane) callbacks.customizeUiComponent(tabs) callbacks.customizeUiComponent(buttonPane) callbacks.customizeUiComponent(utilPane) callbacks.customizeUiComponent(self._basisLabel) callbacks.customizeUiComponent(self._setBasisButton) callbacks.customizeUiComponent(self._hitOnceButton) callbacks.customizeUiComponent(self._autoScanButton) callbacks.customizeUiComponent(self._clearLogButton) callbacks.customizeUiComponent(self._levelSelection) callbacks.customizeUiComponent(self._cancelButton) # Add the custom tab to Burp's UI callbacks.addSuiteTab(self) # Register the context menu and message editor for new tabs callbacks.registerContextMenuFactory(self) # Register as a HTTP listener callbacks.registerHttpListener(self) return
class BurpExtender( IBurpExtender, ITab, IContextMenuFactory, IMessageEditorController): # Implement IBurpExtender def registerExtenderCallbacks(self, callbacks): callbacks.registerContextMenuFactory(self) self._callbacks = callbacks self._helpers = callbacks.getHelpers() callbacks.setExtensionName(EXTENSION_NAME) # Construct UI insets = Insets(3, 3, 3, 3) self._messageEditor = callbacks.createMessageEditor(self, True) attackPanel = self._constructAttackPanel( insets, self._messageEditor.getComponent()) resultsPanel = self._constructResultsPanel(insets) aboutPanel = self._constructAboutPanel(insets) self._tabbedPane = JTabbedPane() self._tabbedPane.addTab("Attack", attackPanel) self._tabbedPane.addTab("Results", resultsPanel) self._tabbedPane.addTab("About", aboutPanel) callbacks.addSuiteTab(self) # Implement ITab def getTabCaption(self): return EXTENSION_NAME def getUiComponent(self): return self._tabbedPane # Implement IMessageEditorController def getHttpService(self): self._updateClassFromUI() return self._httpService def getRequest(self): self._updateClassFromUI() return self._request def getResponse(self): return None # Implement IContextMenuFactory def createMenuItems(self, contextMenuInvocation): messages = contextMenuInvocation.getSelectedMessages() # Only add menu item if a single request is selected if len(messages) == 1: self._contextMenuData = messages menu_item = JMenuItem( "Send to {}".format(EXTENSION_NAME), actionPerformed=self._contextMenuItemClicked ) return [menu_item] def _contextMenuItemClicked(self, _): httpRequestResponse = self._contextMenuData[0] # Update instance variables with request data self._httpService = httpRequestResponse.getHttpService() self._request = httpRequestResponse.getRequest() # Update fields in tab self._hostTextField.setText(self._httpService.getHost()) self._portTextField.setText(str(self._httpService.getPort())) self._protocolCheckBox.setSelected( True if self._httpService.getProtocol() == "https" else False) self._messageEditor.setMessage(self._request, True) def _startAttack(self, _): # Switch to results tab self._tabbedPane.setSelectedIndex(1) # Clear results table self._resultsTableModel.setRowCount(0) # Set progress bar to 0% self._progressBar.setValue(0) Thread(target=self._makeHttpRequests).start() def _makeHttpRequests(self): # Set class variables from values in UI self._updateClassFromUI() self._responses = {} # Set progress bar max to number of requests self._progressBar.setMaximum(len(self._payloads) * self._numReq) for payload in self._payloads: self._responses[payload] = [] # Stick payload into request at specified position # Use lambda function for replacement string to stop slashes being # escaped request = sub("\xa7[^\xa7]*\xa7", lambda x: payload, self._request) request = self._updateContentLength(request) for _ in xrange(self._numReq): # Make request and work out how long it took in ms. This method # is crude, but it's as good as we can get with current Burp # APIs. # See https://support.portswigger.net/customer/portal/questions/16227838-request-response-timing # noqa: E501 startTime = time() response = self._callbacks.makeHttpRequest( self._httpService, request) endTime = time() duration = (endTime - startTime) * 1000 self._progressBar.setValue(self._progressBar.getValue() + 1) self._responses[payload].append(duration) # If all responses for this payload have # been added to array, add to results table. results = self._responses[payload] numReqs = self._numReq statusCode = response.getStatusCode() analysis = self._helpers.analyzeResponse( response.getResponse()) for header in analysis.getHeaders(): if header.lower().startswith("content-length"): content_length = int(header.split(": ")[1]) meanTime = round(mean(results), 3) medianTime = round(median(results), 3) stdDevTime = round(stdDev(results), 3) minTime = int(min(results)) maxTime = int(max(results)) rowData = [ payload, numReqs, statusCode, len(response.getResponse()), content_length, minTime, maxTime, meanTime, medianTime, stdDevTime] self._resultsTableModel.addRow(rowData) def _updateClassFromUI(self): host = self._hostTextField.text port = int(self._portTextField.text) protocol = "https" if self._protocolCheckBox.isSelected() else "http" # In an effort to prevent DNS queries introducing a delay, an attempt # was made to use the IP address of the destination web server instead # of the hostname when building the HttpService. Unfortunately it # caused issues with HTTPS requests, probably because of SNIs. As an # alternative, the hostname is resolved in the next line and hopefully # it will be cached at that point. gethostbyname(host) self._httpService = self._helpers.buildHttpService( host, port, protocol) self._request = self._messageEditor.getMessage() self._numReq = int(self._requestsNumTextField.text) self._payloads = set(self._payloadTextArea.text.split("\n")) def _addPayload(self, _): request = self._messageEditor.getMessage() selection = self._messageEditor.getSelectionBounds() if selection[0] == selection[1]: # No text selected so in/out points are same request.insert(selection[0], 0xa7) request.insert(selection[1], 0xa7) else: request.insert(selection[0], 0xa7) request.insert(selection[1]+1, 0xa7) self._messageEditor.setMessage(request, True) def _clearPayloads(self, _): request = self._messageEditor.getMessage() request = self._helpers.bytesToString(request).replace("\xa7", "") self._messageEditor.setMessage(request, True) def _updateContentLength(self, request): messageSize = len(request) bodyOffset = self._helpers.analyzeRequest(request).getBodyOffset() contentLength = messageSize - bodyOffset contentLengthHeader = "Content-Length: {}".format(contentLength) request = sub("Content-Length: \\d+", contentLengthHeader, request) return request def _constructAttackPanel(self, insets, messageEditorComponent): attackPanel = JPanel(GridBagLayout()) targetHeadingLabel = JLabel("<html><b>Target</b></html>") targetHeadingLabelConstraints = GridBagConstraints() targetHeadingLabelConstraints.gridx = 0 targetHeadingLabelConstraints.gridy = 0 targetHeadingLabelConstraints.gridwidth = 4 targetHeadingLabelConstraints.anchor = GridBagConstraints.LINE_START targetHeadingLabelConstraints.insets = insets attackPanel.add(targetHeadingLabel, targetHeadingLabelConstraints) startAttackButton = JButton("<html><b>Start Attack</b></html>", actionPerformed=self._startAttack) startAttackButtonConstraints = GridBagConstraints() startAttackButtonConstraints.gridx = 4 startAttackButtonConstraints.gridy = 0 startAttackButtonConstraints.insets = insets attackPanel.add(startAttackButton, startAttackButtonConstraints) hostLabel = JLabel("Host:") hostLabelConstraints = GridBagConstraints() hostLabelConstraints.gridx = 0 hostLabelConstraints.gridy = 1 hostLabelConstraints.anchor = GridBagConstraints.LINE_START hostLabelConstraints.insets = insets attackPanel.add(hostLabel, hostLabelConstraints) self._hostTextField = JTextField(25) self._hostTextField.setMinimumSize( self._hostTextField.getPreferredSize()) hostTextFieldConstraints = GridBagConstraints() hostTextFieldConstraints.gridx = 1 hostTextFieldConstraints.gridy = 1 hostTextFieldConstraints.weightx = 1 hostTextFieldConstraints.gridwidth = 2 hostTextFieldConstraints.anchor = GridBagConstraints.LINE_START hostTextFieldConstraints.insets = insets attackPanel.add(self._hostTextField, hostTextFieldConstraints) portLabel = JLabel("Port:") portLabelConstraints = GridBagConstraints() portLabelConstraints.gridx = 0 portLabelConstraints.gridy = 2 portLabelConstraints.anchor = GridBagConstraints.LINE_START portLabelConstraints.insets = insets attackPanel.add(portLabel, portLabelConstraints) self._portTextField = JTextField(5) self._portTextField.setMinimumSize( self._portTextField.getPreferredSize()) portTextFieldConstraints = GridBagConstraints() portTextFieldConstraints.gridx = 1 portTextFieldConstraints.gridy = 2 portTextFieldConstraints.gridwidth = 2 portTextFieldConstraints.anchor = GridBagConstraints.LINE_START portTextFieldConstraints.insets = insets attackPanel.add(self._portTextField, portTextFieldConstraints) self._protocolCheckBox = JCheckBox("Use HTTPS") protocolCheckBoxConstraints = GridBagConstraints() protocolCheckBoxConstraints.gridx = 0 protocolCheckBoxConstraints.gridy = 3 protocolCheckBoxConstraints.gridwidth = 3 protocolCheckBoxConstraints.anchor = GridBagConstraints.LINE_START protocolCheckBoxConstraints.insets = insets attackPanel.add(self._protocolCheckBox, protocolCheckBoxConstraints) requestHeadingLabel = JLabel("<html><b>Request</b></html>") requestHeadingLabelConstraints = GridBagConstraints() requestHeadingLabelConstraints.gridx = 0 requestHeadingLabelConstraints.gridy = 4 requestHeadingLabelConstraints.gridwidth = 4 requestHeadingLabelConstraints.anchor = GridBagConstraints.LINE_START requestHeadingLabelConstraints.insets = insets attackPanel.add(requestHeadingLabel, requestHeadingLabelConstraints) messageEditorComponentConstraints = GridBagConstraints() messageEditorComponentConstraints.gridx = 0 messageEditorComponentConstraints.gridy = 5 messageEditorComponentConstraints.weightx = 1 messageEditorComponentConstraints.weighty = .75 messageEditorComponentConstraints.gridwidth = 4 messageEditorComponentConstraints.gridheight = 2 messageEditorComponentConstraints.fill = GridBagConstraints.BOTH messageEditorComponentConstraints.insets = insets attackPanel.add( messageEditorComponent, messageEditorComponentConstraints) addPayloadButton = JButton( "Add \xa7", actionPerformed=self._addPayload) addPayloadButtonConstraints = GridBagConstraints() addPayloadButtonConstraints.gridx = 4 addPayloadButtonConstraints.gridy = 5 addPayloadButtonConstraints.fill = GridBagConstraints.HORIZONTAL addPayloadButtonConstraints.insets = insets attackPanel.add(addPayloadButton, addPayloadButtonConstraints) clearPayloadButton = JButton( "Clear \xa7", actionPerformed=self._clearPayloads) clearPayloadButtonConstraints = GridBagConstraints() clearPayloadButtonConstraints.gridx = 4 clearPayloadButtonConstraints.gridy = 6 clearPayloadButtonConstraints.anchor = GridBagConstraints.PAGE_START clearPayloadButtonConstraints.fill = GridBagConstraints.HORIZONTAL clearPayloadButtonConstraints.insets = insets attackPanel.add(clearPayloadButton, clearPayloadButtonConstraints) payloadHeadingLabel = JLabel("<html><b>Payloads<b></html>") payloadHeadingLabelConstraints = GridBagConstraints() payloadHeadingLabelConstraints.gridx = 0 payloadHeadingLabelConstraints.gridy = 7 payloadHeadingLabelConstraints.gridwidth = 4 payloadHeadingLabelConstraints.anchor = GridBagConstraints.LINE_START payloadHeadingLabelConstraints.insets = insets attackPanel.add(payloadHeadingLabel, payloadHeadingLabelConstraints) self._payloadTextArea = JTextArea() payloadScrollPane = JScrollPane(self._payloadTextArea) payloadScrollPaneConstraints = GridBagConstraints() payloadScrollPaneConstraints.gridx = 0 payloadScrollPaneConstraints.gridy = 8 payloadScrollPaneConstraints.weighty = .25 payloadScrollPaneConstraints.gridwidth = 3 payloadScrollPaneConstraints.fill = GridBagConstraints.BOTH payloadScrollPaneConstraints.insets = insets attackPanel.add(payloadScrollPane, payloadScrollPaneConstraints) requestsNumLabel = JLabel("Number of requests for each payload:") requestsNumLabelConstraints = GridBagConstraints() requestsNumLabelConstraints.gridx = 0 requestsNumLabelConstraints.gridy = 9 requestsNumLabelConstraints.gridwidth = 2 requestsNumLabelConstraints.anchor = GridBagConstraints.LINE_START requestsNumLabelConstraints.insets = insets attackPanel.add(requestsNumLabel, requestsNumLabelConstraints) self._requestsNumTextField = JTextField("100", 4) self._requestsNumTextField.setMinimumSize( self._requestsNumTextField.getPreferredSize()) requestsNumTextFieldConstraints = GridBagConstraints() requestsNumTextFieldConstraints.gridx = 2 requestsNumTextFieldConstraints.gridy = 9 requestsNumTextFieldConstraints.anchor = GridBagConstraints.LINE_START requestsNumTextFieldConstraints.insets = insets attackPanel.add( self._requestsNumTextField, requestsNumTextFieldConstraints) return attackPanel def _constructResultsPanel(self, insets): resultsPanel = JPanel(GridBagLayout()) self._progressBar = JProgressBar() self._progressBar.setStringPainted(True) self._progressBar.setMinimum(0) progressBarContraints = GridBagConstraints() progressBarContraints.gridx = 0 progressBarContraints.gridy = 0 progressBarContraints.fill = GridBagConstraints.HORIZONTAL resultsPanel.add(self._progressBar, progressBarContraints) self._resultsTableModel = ResultsTableModel(COLUMNS, 0) resultsTable = JTable(self._resultsTableModel) resultsTable.setAutoCreateRowSorter(True) cellRenderer = ColoredTableCellRenderer() for index in [5, 6, 7, 8, 9]: column = resultsTable.columnModel.getColumn(index) column.cellRenderer = cellRenderer resultsTable.getColumnModel().getColumn(0).setPreferredWidth(99999999) resultsTable.getColumnModel().getColumn(1).setMinWidth(160) resultsTable.getColumnModel().getColumn(2).setMinWidth(100) resultsTable.getColumnModel().getColumn(3).setMinWidth(80) resultsTable.getColumnModel().getColumn(4).setMinWidth(80) resultsTable.getColumnModel().getColumn(5).setMinWidth(110) resultsTable.getColumnModel().getColumn(6).setMinWidth(110) resultsTable.getColumnModel().getColumn(7).setMinWidth(90) resultsTable.getColumnModel().getColumn(8).setMinWidth(110) resultsTable.getColumnModel().getColumn(9).setMinWidth(110) resultsTable.setAutoResizeMode(JTable.AUTO_RESIZE_ALL_COLUMNS) resultsScrollPane = JScrollPane(resultsTable) resultsScrollPaneConstraints = GridBagConstraints() resultsScrollPaneConstraints.gridx = 0 resultsScrollPaneConstraints.gridy = 1 resultsScrollPaneConstraints.weightx = 1 resultsScrollPaneConstraints.weighty = 1 resultsScrollPaneConstraints.fill = GridBagConstraints.BOTH resultsPanel.add(resultsScrollPane, resultsScrollPaneConstraints) return resultsPanel def _constructAboutPanel(self, insets): aboutPanel = JPanel(GridBagLayout()) with open("about.html") as file: aboutBody = file.read() aboutLabel = JLabel( aboutBody.format(extension_name=EXTENSION_NAME)) aboutLabelConstraints = GridBagConstraints() aboutLabelConstraints.weightx = 1 aboutLabelConstraints.weighty = 1 aboutLabelConstraints.insets = insets aboutLabelConstraints.fill = GridBagConstraints.HORIZONTAL aboutLabelConstraints.anchor = GridBagConstraints.PAGE_START aboutPanel.add(aboutLabel, aboutLabelConstraints) return aboutPanel
class BurpExtender(IBurpExtender, ITab, IMessageEditorController, AbstractTableModel, IContextMenuFactory): def registerExtenderCallbacks(self, callbacks): # keep a reference to our callbacks object self._callbacks = callbacks # obtain an extension helpers object self._helpers = callbacks.getHelpers() # set our extension name callbacks.setExtensionName("PT Vulnerabilities Manager") self.config = SafeConfigParser() self.createSection('projects') self.createSection('general') self.config.read('config.ini') self.chooser = JFileChooser() # create the log and a lock on which to synchronize when adding log entries self._log = ArrayList() self._lock = Lock() self.logTable = Table(self) self.logTable.getColumnModel().getColumn(0).setMaxWidth(35) self.logTable.getColumnModel().getColumn(1).setMinWidth(100) self._requestViewer = self._callbacks.createMessageEditor(self, False) self._responseViewer = self._callbacks.createMessageEditor(self, False) self.initVulnerabilityTab() self.initProjSettingsTab() self.initTabs() self.initCallbacks() if self.projPath.getText() != None: self.loadVulnerabilities(self.projPath.getText()) print "Thank you for installing PT Vulnerabilities Manager v1.0 extension" print "by Barak Tawily\n\n\n" print "Disclaimer:\nThis extension might create folders and files in your hardisk which might be declared as sensitive information, make sure you are creating projects under encrypted partition" return def initVulnerabilityTab(self): # ## init vulnerability tab # nameLabel = JLabel("Vulnerability Name:") nameLabel.setBounds(10, 10, 140, 30) self.addButton = JButton("Add",actionPerformed=self.addVuln) self.addButton.setBounds(10, 500, 100, 30) rmVulnButton = JButton("Remove",actionPerformed=self.rmVuln) rmVulnButton.setBounds(465, 500, 100, 30) mitigationLabel = JLabel("Mitigation:") mitigationLabel.setBounds(10, 290, 150, 30) addSSBtn = JButton("Add SS",actionPerformed=self.addSS) addSSBtn.setBounds(750, 40, 110, 30) deleteSSBtn = JButton("Remove SS",actionPerformed=self.removeSS) deleteSSBtn.setBounds(750, 75, 110, 30) piclistLabel = JLabel("Images list:") piclistLabel.setBounds(580, 10, 140, 30) self.screenshotsList = DefaultListModel() self.ssList = JList(self.screenshotsList) self.ssList.setBounds(580, 40, 150, 250) self.ssList.addListSelectionListener(ssChangedHandler(self)) self.ssList.setBorder(BorderFactory.createLineBorder(Color.GRAY)) previewPicLabel = JLabel("Selected image preview: (click to open in image viewer)") previewPicLabel.setBounds(580, 290, 500, 30) copyImgMenu = JMenuItem("Copy") copyImgMenu.addActionListener(copyImg(self)) self.imgMenu = JPopupMenu("Popup") self.imgMenu.add(copyImgMenu) self.firstPic = JLabel() self.firstPic.setBorder(BorderFactory.createLineBorder(Color.GRAY)) self.firstPic.setBounds(580, 320, 550, 400) self.firstPic.addMouseListener(imageClicked(self)) self.vulnName = JTextField("") self.vulnName.getDocument().addDocumentListener(vulnTextChanged(self)) self.vulnName.setBounds(140, 10, 422, 30) sevirities = ["Unclassified", "Critical","High","Medium","Low"] self.threatLevel = JComboBox(sevirities); self.threatLevel.setBounds(140, 45, 140, 30) colors = ["Color:", "Green", "Red"] self.colorCombo = JComboBox(colors); self.colorCombo.setBounds(465, 45, 100, 30) self.colorCombo severityLabel = JLabel("Threat Level:") severityLabel.setBounds(10, 45, 100, 30) descriptionLabel = JLabel("Description:") descriptionLabel.setBounds(10, 80, 100, 30) self.descriptionString = JTextArea("", 5, 30) self.descriptionString.setWrapStyleWord(True); self.descriptionString.setLineWrap(True) self.descriptionString.setBounds(10, 110, 555, 175) descriptionStringScroll = JScrollPane(self.descriptionString) descriptionStringScroll.setBounds(10, 110, 555, 175) descriptionStringScroll.setVerticalScrollBarPolicy(ScrollPaneConstants.VERTICAL_SCROLLBAR_AS_NEEDED) self.mitigationStr = JTextArea("", 5, 30) self.mitigationStr.setWrapStyleWord(True); self.mitigationStr.setLineWrap(True) self.mitigationStr.setBounds(10, 320, 555, 175) mitigationStrScroll = JScrollPane(self.mitigationStr) mitigationStrScroll.setBounds(10, 320, 555, 175) mitigationStrScroll.setVerticalScrollBarPolicy(ScrollPaneConstants.VERTICAL_SCROLLBAR_AS_NEEDED) self.pnl = JPanel() self.pnl.setBounds(0, 0, 1000, 1000); self.pnl.setLayout(None); self.pnl.add(addSSBtn) self.pnl.add(piclistLabel) self.pnl.add(nameLabel) self.pnl.add(deleteSSBtn) self.pnl.add(rmVulnButton) self.pnl.add(severityLabel) self.pnl.add(mitigationLabel) self.pnl.add(descriptionLabel) self.pnl.add(previewPicLabel) self.pnl.add(mitigationStrScroll) self.pnl.add(descriptionStringScroll) self.pnl.add(self.ssList) self.pnl.add(self.firstPic) self.pnl.add(self.addButton) self.pnl.add(self.vulnName) self.pnl.add(self.threatLevel) self.pnl.add(self.colorCombo) def initProjSettingsTab(self): # init project settings projNameLabel = JLabel("Name:") projNameLabel.setBounds(10, 50, 140, 30) self.projName = JTextField("") self.projName.setBounds(140, 50, 320, 30) self.projName.getDocument().addDocumentListener(projTextChanged(self)) detailsLabel = JLabel("Details:") detailsLabel.setBounds(10, 120, 140, 30) reportLabel = JLabel("Generate Report:") reportLabel.setBounds(10, 375, 140, 30) types = ["DOCX","HTML","XLSX"] self.reportType = JComboBox(types) self.reportType.setBounds(10, 400, 140, 30) generateReportButton = JButton("Generate", actionPerformed=self.generateReport) generateReportButton.setBounds(160, 400, 90, 30) self.projDetails = JTextArea("", 5, 30) self.projDetails.setWrapStyleWord(True); self.projDetails.setLineWrap(True) projDetailsScroll = JScrollPane(self.projDetails) projDetailsScroll.setBounds(10, 150, 450, 175) projDetailsScroll.setVerticalScrollBarPolicy(ScrollPaneConstants.VERTICAL_SCROLLBAR_AS_NEEDED) projPathLabel = JLabel("Path:") projPathLabel.setBounds(10, 90, 140, 30) self.projPath = JTextField("") self.projPath.setBounds(140, 90, 320, 30) chooseProjPathButton = JButton("Browse...",actionPerformed=self.chooseProjPath) chooseProjPathButton.setBounds(470, 90, 100, 30) importProjButton = JButton("Import",actionPerformed=self.importProj) importProjButton.setBounds(470, 10, 100, 30) exportProjButton = JButton("Export",actionPerformed=self.exportProj) exportProjButton.setBounds(575, 10, 100, 30) openProjButton = JButton("Open Directory",actionPerformed=self.openProj) openProjButton.setBounds(680, 10, 130, 30) currentProjectLabel = JLabel("Current:") currentProjectLabel.setBounds(10, 10, 140, 30) projects = self.config.options('projects') self.currentProject = JComboBox(projects) self.currentProject.addActionListener(projectChangeHandler(self)) self.currentProject.setBounds(140, 10, 140, 30) self.autoSave = JCheckBox("Auto Save Mode") self.autoSave.setEnabled(False) # implement this feature self.autoSave.setBounds(300, 10, 140, 30) self.autoSave.setToolTipText("Will save any changed value while focus is out") addProjButton = JButton("Add / Update",actionPerformed=self.addProj) addProjButton.setBounds(10, 330, 150, 30) removeProjButton = JButton("Remove Current",actionPerformed=self.rmProj) removeProjButton.setBounds(315, 330, 146, 30) generalOptions = self.config.options('general') if 'default project' in generalOptions: defaultProj = self.config.get('general','default project') self.currentProject.getModel().setSelectedItem(defaultProj) self.projPath.setText(self.config.get('projects',self.currentProject.getSelectedItem())) self.clearProjTab = True self.projectSettings = JPanel() self.projectSettings.setBounds(0, 0, 1000, 1000) self.projectSettings.setLayout(None) self.projectSettings.add(reportLabel) self.projectSettings.add(detailsLabel) self.projectSettings.add(projPathLabel) self.projectSettings.add(addProjButton) self.projectSettings.add(openProjButton) self.projectSettings.add(projNameLabel) self.projectSettings.add(projDetailsScroll) self.projectSettings.add(importProjButton) self.projectSettings.add(exportProjButton) self.projectSettings.add(removeProjButton) self.projectSettings.add(generateReportButton) self.projectSettings.add(chooseProjPathButton) self.projectSettings.add(currentProjectLabel) self.projectSettings.add(self.projPath) self.projectSettings.add(self.autoSave) self.projectSettings.add(self.projName) self.projectSettings.add(self.reportType) self.projectSettings.add(self.currentProject) def initTabs(self): # ## init autorize tabs # self._splitpane = JSplitPane(JSplitPane.HORIZONTAL_SPLIT) self.scrollPane = JScrollPane(self.logTable) self._splitpane.setLeftComponent(self.scrollPane) colorsMenu = JMenu("Paint") redMenu = JMenuItem("Red") noneMenu = JMenuItem("None") greenMenu = JMenuItem("Green") redMenu.addActionListener(paintChange(self, "Red")) noneMenu.addActionListener(paintChange(self, None)) greenMenu.addActionListener(paintChange(self, "Green")) colorsMenu.add(redMenu) colorsMenu.add(noneMenu) colorsMenu.add(greenMenu) self.menu = JPopupMenu("Popup") self.menu.add(colorsMenu) self.tabs = JTabbedPane() self.tabs.addTab("Request", self._requestViewer.getComponent()) self.tabs.addTab("Response", self._responseViewer.getComponent()) self.tabs.addTab("Vulnerability", self.pnl) self.tabs.addTab("Project Settings", self.projectSettings) self.tabs.setSelectedIndex(2) self._splitpane.setRightComponent(self.tabs) def initCallbacks(self): # ## init callbacks # # customize our UI components self._callbacks.customizeUiComponent(self._splitpane) self._callbacks.customizeUiComponent(self.logTable) self._callbacks.customizeUiComponent(self.scrollPane) self._callbacks.customizeUiComponent(self.tabs) self._callbacks.registerContextMenuFactory(self) # add the custom tab to Burp's UI self._callbacks.addSuiteTab(self) def loadVulnerabilities(self, projPath): self.clearList(None) selected = False for root, dirs, files in os.walk(projPath): # make it go only for dirs for dirName in dirs: xmlPath = projPath+"/"+dirName+"/vulnerability.xml" # xmlPath = xmlPath.replace("/","//") document = self.getXMLDoc(xmlPath) nodeList = document.getDocumentElement().getChildNodes() vulnName = nodeList.item(0).getTextContent() severity = nodeList.item(1).getTextContent() description = nodeList.item(2).getTextContent() mitigation = nodeList.item(3).getTextContent() color = nodeList.item(4).getTextContent() test = vulnerability(vulnName,severity,description,mitigation,color) self._lock.acquire() row = self._log.size() self._log.add(test) self.fireTableRowsInserted(row, row) self._lock.release() if vulnName == self.vulnName.getText(): self.logTable.setRowSelectionInterval(row,row) selected = True if selected == False and self._log.size() > 0: self.logTable.setRowSelectionInterval(0, 0) self.loadVulnerability(self._log.get(0)) def createSection(self, sectioName): self.config.read('config.ini') if not (sectioName in self.config.sections()): self.config.add_section(sectioName) cfgfile = open("config.ini",'w') self.config.write(cfgfile) cfgfile.close() def saveCfg(self): f = open('config.ini', 'w') self.config.write(f) f.close() def getXMLDoc(self, xmlPath): try: document = DocumentBuilderFactory.newInstance().newDocumentBuilder().parse(xmlPath) return document except: self._extender.popup("XML file not found") return def saveXMLDoc(self, doc, xmlPath): transformerFactory = TransformerFactory.newInstance() transformer = transformerFactory.newTransformer() source = DOMSource(doc) result = StreamResult(File(xmlPath)) transformer.transform(source, result) def generateReport(self,event): if self.reportType.getSelectedItem() == "HTML": path = self.reportToHTML() if self.reportType.getSelectedItem() == "XLSX": path = self.reportToXLS() if self.reportType.getSelectedItem() == "DOCX": path = self.generateReportFromDocxTemplate('template.docx',"newfile.docx", 'word/document.xml') n = JOptionPane.showConfirmDialog(None, "Report generated successfuly:\n%s\nWould you like to open it?" % (path), "PT Manager", JOptionPane.YES_NO_OPTION) if n == JOptionPane.YES_OPTION: os.system('"' + path + '"') # Bug! stucking burp until the file get closed def exportProj(self,event): self.chooser.setDialogTitle("Save project") Ffilter = FileNameExtensionFilter("Zip files", ["zip"]) self.chooser.setFileFilter(Ffilter) returnVal = self.chooser.showSaveDialog(None) if returnVal == JFileChooser.APPROVE_OPTION: dst = str(self.chooser.getSelectedFile()) shutil.make_archive(dst,"zip",self.getCurrentProjPath()) self.popup("Project export successfuly") def importProj(self,event): self.chooser.setDialogTitle("Select project zip to directory") Ffilter = FileNameExtensionFilter("Zip files", ["zip"]) self.chooser.setFileFilter(Ffilter) returnVal = self.chooser.showOpenDialog(None) if returnVal == JFileChooser.APPROVE_OPTION: zipPath = str(self.chooser.getSelectedFile()) self.chooser.setDialogTitle("Select project directory") self.chooser.setFileSelectionMode(JFileChooser.DIRECTORIES_ONLY) returnVal = self.chooser.showOpenDialog(None) if returnVal == JFileChooser.APPROVE_OPTION: projPath = str(self.chooser.getSelectedFile()) + "/PTManager" with zipfile.ZipFile(zipPath, "r") as z: z.extractall(projPath) xmlPath = projPath + "/project.xml" document = self.getXMLDoc(xmlPath) nodeList = document.getDocumentElement().getChildNodes() projName = nodeList.item(0).getTextContent() nodeList.item(1).setTextContent(projPath) self.saveXMLDoc(document, xmlPath) self.config.set('projects', projName, projPath) self.saveCfg() self.reloadProjects() self.currentProject.getModel().setSelectedItem(projName) self.clearVulnerabilityTab() def reportToXLS(self): if not xlsxwriterImported: self.popup("xlsxwriter library is not imported") return workbook = xlsxwriter.Workbook(self.getCurrentProjPath() + '/PT Manager Report.xlsx') worksheet = workbook.add_worksheet() bold = workbook.add_format({'bold': True}) worksheet.write(0, 0, "Vulnerability Name", bold) worksheet.write(0, 1, "Threat Level", bold) worksheet.write(0, 2, "Description", bold) worksheet.write(0, 3, "Mitigation", bold) row = 1 for i in range(0,self._log.size()): worksheet.write(row, 0, self._log.get(i).getName()) worksheet.write(row, 1, self._log.get(i).getSeverity()) worksheet.write(row, 2, self._log.get(i).getDescription()) worksheet.write(row, 3, self._log.get(i).getMitigation()) row = row + 1 # add requests and images as well workbook.close() return self.getCurrentProjPath() + '/PT Manager Report.xlsx' def reportToHTML(self): htmlContent = """<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> <html xmlns="http://www.w3.org/1999/xhtml" lang="he" dir="ltr"> <head> <title>PT Manager Report</title> <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" /> <style> body { background-repeat: no-repeat; background-attachment: fixed; font-family: Arial,Tahoma,sens-serif; font-size: 13px; margin: auto; } #warpcenter { width: 900px; margin: 0px auto; } table { border: 2px dashed #000000; } td { border-top: 2px dashed #000000; padding: 10px; } img { border: 0px; } </style> <script language="javascript"> function divHideShow(divToHideOrShow) { var div = document.getElementById(divToHideOrShow); if (div.style.display == "block") { div.style.display = "none"; } else { div.style.display = "block"; } } </script> </head> <body> <div id="warpcenter"> <h1> PT Manager Report </h1> <h2> Project: %s</h1> """ % (self.projName.getText()) for i in range(0,self._log.size()): name = self._log.get(i).getName() request = "None" response = "None" path = self.getVulnReqResPath("request",name) if os.path.exists(path): request = self.newlineToBR(self.getFileContent(path)) path = self.getVulnReqResPath("response",name) if os.path.exists(path): response = self.newlineToBR(self.getFileContent(path)) images = "" for fileName in os.listdir(self.projPath.getText()+"/"+self.clearStr(name)): if fileName.endswith(".jpg"): images += "%s<br><img src=\"%s\"><br><br>" % (fileName, self.projPath.getText()+"/"+self.clearStr(name) + "/" + fileName) description = self.newlineToBR(self._log.get(i).getDescription()) mitigation = self.newlineToBR(self._log.get(i).getMitigation()) htmlContent += self.convertVulntoTable(i,name,self._log.get(i).getSeverity(), description,mitigation, request, response, images) htmlContent += "</div></body></html>" f = open(self.getCurrentProjPath() + '/PT Manager Report.html', 'w') f.writelines(htmlContent) f.close() return self.getCurrentProjPath() + '/PT Manager Report.html' def newlineToBR(self,string): return "<br />".join(string.split("\n")) def getFileContent(self,path): f = open(path, "rb") content = f.read() f.close() return content def convertVulntoTable(self, number, name, severity, description, mitigation, request = "None", response = "None", images = "None"): return """<div style="width: 100%%;height: 30px;text-align: center;background-color:#E0E0E0;font-size: 17px;font-weight: bold;color: #000;padding-top: 10px;">%s <a href="javascript:divHideShow('Table_%s');" style="color:#191970">(OPEN / CLOSE)</a></div> <div id="Table_%s" style="display: none;"> <table width="100%%" cellspacing="0" cellpadding="0" style="margin: 0px auto;text-align: left;border-top: 0px;"> <tr> <td> <div style="font-size: 16px;font-weight: bold;"> <span style="color:#000000">Threat Level: </span> <span style="color:#8b8989">%s</span> </td> </tr> <tr> <td> <div style="font-size: 16px;font-weight: bold;"> <span style="color:#000000">Description</span> <a href="javascript:divHideShow('Table_%s_Command_03');" style="color:#191970">OPEN / CLOSE >>></a> </div> <div id="Table_%s_Command_03" style="display: none;margin-top: 25px;"> %s </div> </td> </tr> <tr> <td> <div style="font-size: 16px;font-weight: bold;"> <span style="color:#000000">Mitigration</span> <a href="javascript:divHideShow('Table_%s_Command_04');" style="color:#191970">OPEN / CLOSE >>></a> </div> <div id="Table_%s_Command_04" style="display: none;margin-top: 25px;"> %s <b> </td> </tr> <tr> <td> <div style="font-size: 16px;font-weight: bold;"> <span style="color:#000000">Request</span> <a href="javascript:divHideShow('Table_%s_Command_05');" style="color:#191970">OPEN / CLOSE >>></a> </div> <div id="Table_%s_Command_05" style="display: none;margin-top: 25px;"> %s <b> </td> </tr> <tr> <td> <div style="font-size: 16px;font-weight: bold;"> <span style="color:#000000">Response</span> <a href="javascript:divHideShow('Table_%s_Command_06');" style="color:#191970">OPEN / CLOSE >>></a> </div> <div id="Table_%s_Command_06" style="display: none;margin-top: 25px;"> %s <b> </td> </tr> <tr> <td> <div style="font-size: 16px;font-weight: bold;"> <span style="color:#000000">Images</span> <a href="javascript:divHideShow('Table_%s_Command_07');" style="color:#191970">OPEN / CLOSE >>></a> </div> <div id="Table_%s_Command_07" style="display: none;margin-top: 25px;"> %s <b> </td> </tr> </table> </div><br><br>""" % (name,number,number,severity,number,number,description,number,number,mitigation,number,number,request,number,number,response,number,number,images) def clearVulnerabilityTab(self, rmVuln=True): if rmVuln: self.vulnName.setText("") self.descriptionString.setText("") self.mitigationStr.setText("") self.colorCombo.setSelectedIndex(0) self.threatLevel.setSelectedIndex(0) self.screenshotsList.clear() self.addButton.setText("Add") self.firstPic.setIcon(None) def saveRequestResponse(self, type, requestResponse, vulnName): path = self.getVulnReqResPath(type,vulnName) f = open(path, 'wb') f.write(requestResponse) f.close() def openProj(self, event): os.system('explorer ' + self.projPath.getText()) def getVulnReqResPath(self, requestOrResponse, vulnName): return self.getCurrentProjPath() + "/" + self.clearStr(vulnName) + "/"+requestOrResponse+"_" + self.clearStr(vulnName) def htmlEscape(self,data): return data.replace('&', '&').replace('<', '<').replace('>', '>').replace('"', '"').replace("'", ''') def generateReportFromDocxTemplate(self, zipname, newZipName, filename): newZipName = self.getCurrentProjPath() + "/" + newZipName with zipfile.ZipFile(zipname, 'r') as zin: with zipfile.ZipFile(newZipName, 'w') as zout: zout.comment = zin.comment for item in zin.infolist(): if item.filename != filename: zout.writestr(item, zin.read(item.filename)) else: xml_content = zin.read(item.filename) result = re.findall("(.*)<w:body>(?:.*)<\/w:body>(.*)",xml_content)[0] newXML = result[0] templateBody = re.findall("<w:body>(.*)<\/w:body>", xml_content)[0] newBody = "" for i in range(0,self._log.size()): tmp = templateBody tmp = tmp.replace("$vulnerability", self.htmlEscape(self._log.get(i).getName())) tmp = tmp.replace("$severity", self.htmlEscape(self._log.get(i).getSeverity())) tmp = tmp.replace("$description", self.htmlEscape(self._log.get(i).getDescription())) tmp = tmp.replace("$mitigation", self.htmlEscape(self._log.get(i).getMitigation())) newBody = newBody + tmp newXML = newXML + newBody newXML = newXML + result[1] with zipfile.ZipFile(newZipName, mode='a', compression=zipfile.ZIP_DEFLATED) as zf: zf.writestr(filename, newXML) return newZipName def chooseProjPath(self, event): self.chooser.setDialogTitle("Select target directory") self.chooser.setFileSelectionMode(JFileChooser.DIRECTORIES_ONLY) returnVal = self.chooser.showOpenDialog(None) if returnVal == JFileChooser.APPROVE_OPTION: projPath = str(self.chooser.getSelectedFile()) + "/PTManager" os.makedirs(projPath) self.projPath.setText(projPath) def reloadProjects(self): self.currentProject.setModel(DefaultComboBoxModel(self.config.options('projects'))) def rmProj(self, event): if self.popUpAreYouSure() == JOptionPane.YES_OPTION: self._requestViewer.setMessage("None", False) self._responseViewer.setMessage("None", False) shutil.rmtree(self.projPath.getText()) self.config.remove_option('projects',self.currentProject.getSelectedItem()) self.reloadProjects() self.currentProject.setSelectedIndex(0) self.loadVulnerabilities(self.projPath.getText()) def popup(self,msg): JOptionPane.showMessageDialog(None,msg) def addProj(self, event): projPath = self.projPath.getText() if projPath == None or projPath == "": self.popup("Please select path") return self.config.set('projects', self.projName.getText(), projPath) self.saveCfg() xml = ET.Element('project') name = ET.SubElement(xml, "name") path = ET.SubElement(xml, "path") details = ET.SubElement(xml, "details") autoSaveMode = ET.SubElement(xml, "autoSaveMode") name.text = self.projName.getText() path.text = projPath details.text = self.projDetails.getText() autoSaveMode.text = str(self.autoSave.isSelected()) tree = ET.ElementTree(xml) try: tree.write(self.getCurrentProjPath()+'/project.xml') except: self.popup("Invalid path") return self.reloadProjects() self.clearVulnerabilityTab() self.clearList(None) self.currentProject.getModel().setSelectedItem(self.projName.getText()) def resize(self, image, width, height): bi = BufferedImage(width, height, BufferedImage.TRANSLUCENT) g2d = bi.createGraphics() g2d.addRenderingHints(RenderingHints(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY)) g2d.drawImage(image, 0, 0, width, height, None) g2d.dispose() return bi; def clearStr(self, var): return var.replace(" " , "_").replace("\\" , "").replace("/" , "").replace(":" , "").replace("*" , "").replace("?" , "").replace("\"" , "").replace("<" , "").replace(">" , "").replace("|" , "").replace("(" , "").replace(")" , "") def popUpAreYouSure(self): dialogResult = JOptionPane.showConfirmDialog(None,"Are you sure?","Warning",JOptionPane.YES_NO_OPTION) if dialogResult == 0: return 0 return 1 def removeSS(self,event): if self.popUpAreYouSure() == JOptionPane.YES_OPTION: os.remove(self.getCurrentVulnPath() + "/" + self.ssList.getSelectedValue()) self.ssList.getModel().remove(self.ssList.getSelectedIndex()) self.firstPic.setIcon(ImageIcon(None)) # check if there is images and select the first one # bug in linux def addSS(self,event): clipboard = Toolkit.getDefaultToolkit().getSystemClipboard() try: image = clipboard.getData(DataFlavor.imageFlavor) except: self.popup("Clipboard not contains image") return vulnPath = self.projPath.getText() + "/" + self.clearStr(self.vulnName.getText()) if not os.path.exists(vulnPath): os.makedirs(vulnPath) name = self.clearStr(self.vulnName.getText()) + str(random.randint(1, 99999))+".jpg" fileName = self.projPath.getText()+"/"+ self.clearStr(self.vulnName.getText()) + "/" + name file = File(fileName) bufferedImage = BufferedImage(image.getWidth(None), image.getHeight(None), BufferedImage.TYPE_INT_RGB); g = bufferedImage.createGraphics(); g.drawImage(image, 0, 0, bufferedImage.getWidth(), bufferedImage.getHeight(), Color.WHITE, None); ImageIO.write(bufferedImage, "jpg", file) self.addVuln(self) self.ssList.setSelectedValue(name,True) def rmVuln(self, event): if self.popUpAreYouSure() == JOptionPane.YES_OPTION: self._requestViewer.setMessage("None", False) self._responseViewer.setMessage("None", False) shutil.rmtree(self.getCurrentVulnPath()) self.clearVulnerabilityTab() self.loadVulnerabilities(self.getCurrentProjPath()) def addVuln(self, event): if self.colorCombo.getSelectedItem() == "Color:": colorTxt = None else: colorTxt = self.colorCombo.getSelectedItem() self._lock.acquire() row = self._log.size() vulnObject = vulnerability(self.vulnName.getText(),self.threatLevel.getSelectedItem(),self.descriptionString.getText(),self.mitigationStr.getText() ,colorTxt) self._log.add(vulnObject) self.fireTableRowsInserted(row, row) self._lock.release() vulnPath = self.projPath.getText() + "/" + self.clearStr(self.vulnName.getText()) if not os.path.exists(vulnPath): os.makedirs(vulnPath) xml = ET.Element('vulnerability') name = ET.SubElement(xml, "name") severity = ET.SubElement(xml, "severity") description = ET.SubElement(xml, "description") mitigation = ET.SubElement(xml, "mitigation") color = ET.SubElement(xml, "color") name.text = self.vulnName.getText() severity.text = self.threatLevel.getSelectedItem() description.text = self.descriptionString.getText() mitigation.text = self.mitigationStr.getText() color.text = colorTxt tree = ET.ElementTree(xml) tree.write(vulnPath+'/vulnerability.xml') self.loadVulnerabilities(self.getCurrentProjPath()) self.loadVulnerability(vulnObject) def vulnNameChanged(self): if os.path.exists(self.getCurrentVulnPath()) and self.vulnName.getText() != "": self.addButton.setText("Update") elif self.addButton.getText() != "Add": options = ["Create a new vulnerability", "Change current vulnerability name"] n = JOptionPane.showOptionDialog(None, "Would you like to?", "Vulnerability Name", JOptionPane.YES_NO_CANCEL_OPTION, JOptionPane.QUESTION_MESSAGE, None, options, options[0]); if n == 0: self.clearVulnerabilityTab(False) self.addButton.setText("Add") else: newName = JOptionPane.showInputDialog( None, "Enter new name:", "Vulnerability Name", JOptionPane.PLAIN_MESSAGE, None, None, self.vulnName.getText()) row = self.logTable.getSelectedRow() old = self.logTable.getValueAt(row,1) self.changeVulnName(newName,old) def changeVulnName(self,new,old): newpath = self.getCurrentProjPath() + "/" + new oldpath = self.getCurrentProjPath() + "/" + old os.rename(oldpath,newpath) self.changeCurrentVuln(new,0, newpath + "/vulnerability.xml") def getCurrentVulnPath(self): return self.projPath.getText() + "/" + self.clearStr(self.vulnName.getText()) def getCurrentProjPath(self): return self.projPath.getText() def loadSS(self, imgPath): image = ImageIO.read(File(imgPath)) if image.getWidth() <= 550 and image.getHeight() <= 400: self.firstPic.setIcon(ImageIcon(image)) self.firstPic.setSize(image.getWidth(),image.getHeight()) else: self.firstPic.setIcon(ImageIcon(self.resize(image,550, 400))) self.firstPic.setSize(550,400) def clearProjectTab(self): self.projPath.setText("") self.projDetails.setText("") def clearList(self, event): self._lock.acquire() self._log = ArrayList() row = self._log.size() self.fireTableRowsInserted(row, row) self._lock.release() # # implement IContextMenuFactory # def createMenuItems(self, invocation): responses = invocation.getSelectedMessages(); if responses > 0: ret = LinkedList() requestMenuItem = JMenuItem("Send to PT Manager"); requestMenuItem.addActionListener(handleMenuItems(self,responses[0], "request")) ret.add(requestMenuItem); return(ret); return null; # # implement ITab # def getTabCaption(self): return "PT Manager" def getUiComponent(self): return self._splitpane # # extend AbstractTableModel # def getRowCount(self): try: return self._log.size() except: return 0 def getColumnCount(self): return 3 def getColumnName(self, columnIndex): if columnIndex == 0: return "#" if columnIndex == 1: return "Vulnerability Name" if columnIndex == 2: return "Threat Level" return "" def getValueAt(self, rowIndex, columnIndex): vulnObject = self._log.get(rowIndex) if columnIndex == 0: return rowIndex+1 if columnIndex == 1: return vulnObject.getName() if columnIndex == 2: return vulnObject.getSeverity() if columnIndex == 3: return vulnObject.getMitigation() if columnIndex == 4: return vulnObject.getColor() return "" def changeCurrentVuln(self,value,fieldNumber, xmlPath = "def"): if xmlPath == "def": xmlPath = self.getCurrentVulnPath() + "/vulnerability.xml" document = self.getXMLDoc(xmlPath) nodeList = document.getDocumentElement().getChildNodes() nodeList.item(fieldNumber).setTextContent(value) self.saveXMLDoc(document, xmlPath) self.loadVulnerabilities(self.getCurrentProjPath()) def loadVulnerability(self, vulnObject): self.addButton.setText("Update") self.vulnName.setText(vulnObject.getName()) self.threatLevel.setSelectedItem(vulnObject.getSeverity()) self.descriptionString.setText(vulnObject.getDescription()) self.mitigationStr.setText(vulnObject.getMitigation()) if vulnObject.getColor() == "" or vulnObject.getColor() == None: self.colorCombo.setSelectedItem("Color:") else: self.colorCombo.setSelectedItem(vulnObject.getColor()) self.screenshotsList.clear() for fileName in os.listdir(self.projPath.getText()+"/"+self.clearStr(vulnObject.getName())): if fileName.endswith(".jpg"): self.screenshotsList.addElement(fileName) imgPath = self.projPath.getText()+"/"+self.clearStr(vulnObject.getName())+'/'+fileName # imgPath = imgPath.replace("/","//") self.loadSS(imgPath) if (self.screenshotsList.getSize() == 0): self.firstPic.setIcon(None) else: self.ssList.setSelectedIndex(0) path = self.getVulnReqResPath("request",vulnObject.getName()) if os.path.exists(path): f = self.getFileContent(path) self._requestViewer.setMessage(f, False) else: self._requestViewer.setMessage("None", False) path = self.getVulnReqResPath("response",vulnObject.getName()) if os.path.exists(path): f = self.getFileContent(path) self._responseViewer.setMessage(f, False) else: self._responseViewer.setMessage("None", False)
class BurpExtender(IBurpExtender, ITab, IHttpListener, IMessageEditorController, AbstractTableModel, IContextMenuFactory): def registerExtenderCallbacks(self, callbacks): # keep a reference to our callbacks object self._callbacks = callbacks # obtain an extension helpers object self._helpers = callbacks.getHelpers() # set our extension name callbacks.setExtensionName("Autorize") # create the log and a lock on which to synchronize when adding log entries self._log = ArrayList() self._lock = Lock() self._enfocementStatuses = ["Authorization bypass!","Authorization enforced??? (please configure enforcement detector)","Authorization enforced!"] self.intercept = 0 self.initInterceptionFilters() self.initEnforcementDetector() self.initEnforcementDetectorUnauthorized() self.initExport() self.initConfigurationTab() self.initTabs() self.initCallbacks() self.currentRequestNumber = 1 print "Thank you for installing Autorize v0.12 extension" print "Created by Barak Tawily" print "Contributors: Barak Tawily, Federico Dotta" print "\nGithub:\nhttps://github.com/Quitten/Autorize" return def initExport(self): # ## init enforcement detector tab # exportLType = JLabel("File Type:") exportLType.setBounds(10, 10, 100, 30) exportLES = JLabel("Enforcement Statuses:") exportLES.setBounds(10, 50, 160, 30) exportFileTypes = ["HTML","CSV"] self.exportType = JComboBox(exportFileTypes) self.exportType.setBounds(100, 10, 200, 30) exportES = ["All Statuses", self._enfocementStatuses[0], self._enfocementStatuses[1], self._enfocementStatuses[2]] self.exportES = JComboBox(exportES) self.exportES.setBounds(100, 50, 200, 30) exportLES = JLabel("Statuses:") exportLES.setBounds(10, 50, 100, 30) self.exportButton = JButton("Export",actionPerformed=self.export) self.exportButton.setBounds(390, 25, 100, 30) self.exportPnl = JPanel() self.exportPnl.setLayout(None); self.exportPnl.setBounds(0, 0, 1000, 1000); self.exportPnl.add(exportLType) self.exportPnl.add(self.exportType) self.exportPnl.add(exportLES) self.exportPnl.add(self.exportES) self.exportPnl.add(self.exportButton) def initEnforcementDetector(self): # ## init enforcement detector tab # # These two variable appears to be unused... self.EDFP = ArrayList() self.EDCT = ArrayList() EDLType = JLabel("Type:") EDLType.setBounds(10, 10, 140, 30) EDLContent = JLabel("Content:") EDLContent.setBounds(10, 50, 140, 30) EDLabelList = JLabel("Filter List:") EDLabelList.setBounds(10, 165, 140, 30) EDStrings = ["Headers (simple string): (enforced message headers contains)", "Headers (regex): (enforced messege headers contains)", "Body (simple string): (enforced messege body contains)", "Body (regex): (enforced messege body contains)", "Full request (simple string): (enforced messege contains)", "Full request (regex): (enforced messege contains)", "Content-Length: (constant Content-Length number of enforced response)"] self.EDType = JComboBox(EDStrings) self.EDType.setBounds(80, 10, 430, 30) self.EDText = JTextArea("", 5, 30) self.EDText.setBounds(80, 50, 300, 110) self.EDModel = DefaultListModel(); self.EDList = JList(self.EDModel); self.EDList.setBounds(80, 175, 300, 110) self.EDList.setBorder(LineBorder(Color.BLACK)) self.EDAdd = JButton("Add filter",actionPerformed=self.addEDFilter) self.EDAdd.setBounds(390, 85, 120, 30) self.EDDel = JButton("Remove filter",actionPerformed=self.delEDFilter) self.EDDel.setBounds(390, 210, 120, 30) self.EDPnl = JPanel() self.EDPnl.setLayout(None); self.EDPnl.setBounds(0, 0, 1000, 1000); self.EDPnl.add(EDLType) self.EDPnl.add(self.EDType) self.EDPnl.add(EDLContent) self.EDPnl.add(self.EDText) self.EDPnl.add(self.EDAdd) self.EDPnl.add(self.EDDel) self.EDPnl.add(EDLabelList) self.EDPnl.add(self.EDList) def initEnforcementDetectorUnauthorized(self): # ## init enforcement detector tab # EDLType = JLabel("Type:") EDLType.setBounds(10, 10, 140, 30) EDLContent = JLabel("Content:") EDLContent.setBounds(10, 50, 140, 30) EDLabelList = JLabel("Filter List:") EDLabelList.setBounds(10, 165, 140, 30) EDStrings = ["Headers (simple string): (enforced message headers contains)", "Headers (regex): (enforced messege headers contains)", "Body (simple string): (enforced messege body contains)", "Body (regex): (enforced messege body contains)", "Full request (simple string): (enforced messege contains)", "Full request (regex): (enforced messege contains)", "Content-Length: (constant Content-Length number of enforced response)"] self.EDTypeUnauth = JComboBox(EDStrings) self.EDTypeUnauth.setBounds(80, 10, 430, 30) self.EDTextUnauth = JTextArea("", 5, 30) self.EDTextUnauth.setBounds(80, 50, 300, 110) self.EDModelUnauth = DefaultListModel(); self.EDListUnauth = JList(self.EDModelUnauth); self.EDListUnauth.setBounds(80, 175, 300, 110) self.EDListUnauth.setBorder(LineBorder(Color.BLACK)) self.EDAddUnauth = JButton("Add filter",actionPerformed=self.addEDFilterUnauth) self.EDAddUnauth.setBounds(390, 85, 120, 30) self.EDDelUnauth = JButton("Remove filter",actionPerformed=self.delEDFilterUnauth) self.EDDelUnauth.setBounds(390, 210, 120, 30) self.EDPnlUnauth = JPanel() self.EDPnlUnauth.setLayout(None); self.EDPnlUnauth.setBounds(0, 0, 1000, 1000); self.EDPnlUnauth.add(EDLType) self.EDPnlUnauth.add(self.EDTypeUnauth) self.EDPnlUnauth.add(EDLContent) self.EDPnlUnauth.add(self.EDTextUnauth) self.EDPnlUnauth.add(self.EDAddUnauth) self.EDPnlUnauth.add(self.EDDelUnauth) self.EDPnlUnauth.add(EDLabelList) self.EDPnlUnauth.add(self.EDListUnauth) def initInterceptionFilters(self): # ## init interception filters tab # IFStrings = ["Scope items only: (Content is not required)","URL Contains (simple string): ","URL Contains (regex): ","URL Not Contains (simple string): ","URL Not Contains (regex): "] self.IFType = JComboBox(IFStrings) self.IFType.setBounds(80, 10, 430, 30) self.IFModel = DefaultListModel(); self.IFList = JList(self.IFModel); self.IFList.setBounds(80, 175, 300, 110) self.IFList.setBorder(LineBorder(Color.BLACK)) self.IFText = JTextArea("", 5, 30) self.IFText.setBounds(80, 50, 300, 110) IFLType = JLabel("Type:") IFLType.setBounds(10, 10, 140, 30) IFLContent = JLabel("Content:") IFLContent.setBounds(10, 50, 140, 30) IFLabelList = JLabel("Filter List:") IFLabelList.setBounds(10, 165, 140, 30) self.IFAdd = JButton("Add filter",actionPerformed=self.addIFFilter) self.IFAdd.setBounds(390, 85, 120, 30) self.IFDel = JButton("Remove filter",actionPerformed=self.delIFFilter) self.IFDel.setBounds(390, 210, 120, 30) self.filtersPnl = JPanel() self.filtersPnl.setLayout(None); self.filtersPnl.setBounds(0, 0, 1000, 1000); self.filtersPnl.add(IFLType) self.filtersPnl.add(self.IFType) self.filtersPnl.add(IFLContent) self.filtersPnl.add(self.IFText) self.filtersPnl.add(self.IFAdd) self.filtersPnl.add(self.IFDel) self.filtersPnl.add(IFLabelList) self.filtersPnl.add(self.IFList) def initConfigurationTab(self): # ## init configuration tab # self.prevent304 = JCheckBox("Prevent 304 Not Modified status code") self.prevent304.setBounds(290, 25, 300, 30) self.ignore304 = JCheckBox("Ignore 304/204 status code responses") self.ignore304.setBounds(290, 5, 300, 30) self.ignore304.setSelected(True) self.autoScroll = JCheckBox("Auto Scroll") #self.autoScroll.setBounds(290, 45, 140, 30) self.autoScroll.setBounds(160, 40, 140, 30) self.doUnauthorizedRequest = JCheckBox("Check unauthenticated") self.doUnauthorizedRequest.setBounds(290, 45, 300, 30) self.doUnauthorizedRequest.setSelected(True) startLabel = JLabel("Authorization checks:") startLabel.setBounds(10, 10, 140, 30) self.startButton = JButton("Autorize is off",actionPerformed=self.startOrStop) self.startButton.setBounds(160, 10, 120, 30) self.startButton.setBackground(Color(255, 100, 91, 255)) self.clearButton = JButton("Clear List",actionPerformed=self.clearList) self.clearButton.setBounds(10, 40, 100, 30) self.replaceString = JTextArea("Cookie: Insert=injected; header=here;", 5, 30) self.replaceString.setWrapStyleWord(True); self.replaceString.setLineWrap(True) self.replaceString.setBounds(10, 80, 470, 180) self.filtersTabs = JTabbedPane() self.filtersTabs.addTab("Enforcement Detector", self.EDPnl) self.filtersTabs.addTab("Detector Unauthenticated", self.EDPnlUnauth) self.filtersTabs.addTab("Interception Filters", self.filtersPnl) self.filtersTabs.addTab("Export", self.exportPnl) self.filtersTabs.setBounds(0, 280, 2000, 700) self.pnl = JPanel() self.pnl.setBounds(0, 0, 1000, 1000); self.pnl.setLayout(None); self.pnl.add(self.startButton) self.pnl.add(self.clearButton) self.pnl.add(self.replaceString) self.pnl.add(startLabel) self.pnl.add(self.autoScroll) self.pnl.add(self.ignore304) self.pnl.add(self.prevent304) self.pnl.add(self.doUnauthorizedRequest) self.pnl.add(self.filtersTabs) def initTabs(self): # ## init autorize tabs # self.logTable = Table(self) self.logTable.setAutoCreateRowSorter(True) tableWidth = self.logTable.getPreferredSize().width self.logTable.getColumn("ID").setPreferredWidth(Math.round(tableWidth / 50 * 2)) self.logTable.getColumn("URL").setPreferredWidth(Math.round(tableWidth / 50 * 24)) self.logTable.getColumn("Orig. Length").setPreferredWidth(Math.round(tableWidth / 50 * 4)) self.logTable.getColumn("Modif. Length").setPreferredWidth(Math.round(tableWidth / 50 * 4)) self.logTable.getColumn("Unauth. Length").setPreferredWidth(Math.round(tableWidth / 50 * 4)) self.logTable.getColumn("Authorization Enforcement Status").setPreferredWidth(Math.round(tableWidth / 50 * 4)) self.logTable.getColumn("Authorization Unauth. Status").setPreferredWidth(Math.round(tableWidth / 50 * 4)) self._splitpane = JSplitPane(JSplitPane.HORIZONTAL_SPLIT) self._splitpane.setResizeWeight(1) self.scrollPane = JScrollPane(self.logTable) self._splitpane.setLeftComponent(self.scrollPane) self.scrollPane.getVerticalScrollBar().addAdjustmentListener(autoScrollListener(self)) self.menuES0 = JCheckBoxMenuItem(self._enfocementStatuses[0],True) self.menuES1 = JCheckBoxMenuItem(self._enfocementStatuses[1],True) self.menuES2 = JCheckBoxMenuItem(self._enfocementStatuses[2],True) self.menuES0.addItemListener(menuTableFilter(self)) self.menuES1.addItemListener(menuTableFilter(self)) self.menuES2.addItemListener(menuTableFilter(self)) copyURLitem = JMenuItem("Copy URL"); copyURLitem.addActionListener(copySelectedURL(self)) self.menu = JPopupMenu("Popup") self.menu.add(copyURLitem) self.menu.add(self.menuES0) self.menu.add(self.menuES1) self.menu.add(self.menuES2) self.tabs = JTabbedPane() self._requestViewer = self._callbacks.createMessageEditor(self, False) self._responseViewer = self._callbacks.createMessageEditor(self, False) self._originalrequestViewer = self._callbacks.createMessageEditor(self, False) self._originalresponseViewer = self._callbacks.createMessageEditor(self, False) self._unauthorizedrequestViewer = self._callbacks.createMessageEditor(self, False) self._unauthorizedresponseViewer = self._callbacks.createMessageEditor(self, False) self.tabs.addTab("Modified Request", self._requestViewer.getComponent()) self.tabs.addTab("Modified Response", self._responseViewer.getComponent()) self.tabs.addTab("Original Request", self._originalrequestViewer.getComponent()) self.tabs.addTab("Original Response", self._originalresponseViewer.getComponent()) self.tabs.addTab("Unauthenticated Request", self._unauthorizedrequestViewer.getComponent()) self.tabs.addTab("Unauthenticated Response", self._unauthorizedresponseViewer.getComponent()) self.tabs.addTab("Configuration", self.pnl) self.tabs.setSelectedIndex(6) self._splitpane.setRightComponent(self.tabs) def initCallbacks(self): # ## init callbacks # # customize our UI components self._callbacks.customizeUiComponent(self._splitpane) self._callbacks.customizeUiComponent(self.logTable) self._callbacks.customizeUiComponent(self.scrollPane) self._callbacks.customizeUiComponent(self.tabs) self._callbacks.customizeUiComponent(self.filtersTabs) self._callbacks.registerContextMenuFactory(self) # add the custom tab to Burp's UI self._callbacks.addSuiteTab(self) # ## Events functions # def startOrStop(self, event): if self.startButton.getText() == "Autorize is off": self.startButton.setText("Autorize is on") self.startButton.setBackground(Color.GREEN) self.intercept = 1 self._callbacks.registerHttpListener(self) else: self.startButton.setText("Autorize is off") self.startButton.setBackground(Color(255, 100, 91, 255)) self.intercept = 0 self._callbacks.removeHttpListener(self) def addEDFilter(self, event): typeName = self.EDType.getSelectedItem().split(":")[0] self.EDModel.addElement(typeName + ": " + self.EDText.getText()) def delEDFilter(self, event): index = self.EDList.getSelectedIndex(); if not index == -1: self.EDModel.remove(index); def addEDFilterUnauth(self, event): typeName = self.EDTypeUnauth.getSelectedItem().split(":")[0] self.EDModelUnauth.addElement(typeName + ": " + self.EDTextUnauth.getText()) def delEDFilterUnauth(self, event): index = self.EDListUnauth.getSelectedIndex(); if not index == -1: self.EDModelUnauth.remove(index); def addIFFilter(self, event): typeName = self.IFType.getSelectedItem().split(":")[0] self.IFModel.addElement(typeName + ": " + self.IFText.getText()) def delIFFilter(self, event): index = self.IFList.getSelectedIndex(); if not index == -1: self.IFModel.remove(index); def clearList(self, event): self._lock.acquire() oldSize = self._log.size() self._log.clear() self.fireTableRowsDeleted(0, oldSize - 1) self._lock.release() def export(self, event): if self.exportType.getSelectedItem() == "HTML": self.exportToHTML() else: self.exportToCSV() def exportToCSV(self): parentFrame = JFrame() fileChooser = JFileChooser() fileChooser.setSelectedFile(File("AutorizeReprort.csv")); fileChooser.setDialogTitle("Save Autorize Report") userSelection = fileChooser.showSaveDialog(parentFrame) if userSelection == JFileChooser.APPROVE_OPTION: fileToSave = fileChooser.getSelectedFile() enforcementStatusFilter = self.exportES.getSelectedItem() csvContent = "id\tURL\tOriginal length\tModified length\tUnauthorized length\tAuthorization Enforcement Status\tAuthorization Unauthenticated Status\n" for i in range(0,self._log.size()): if enforcementStatusFilter == "All Statuses": csvContent += "%d\t%s\t%d\t%d\t%d\t%s\t%s\n" % (self._log.get(i)._id,self._log.get(i)._url, len(self._log.get(i)._originalrequestResponse.getResponse()) if self._log.get(i)._originalrequestResponse != None else 0, len(self._log.get(i)._requestResponse.getResponse()) if self._log.get(i)._requestResponse != None else 0, len(self._log.get(i)._unauthorizedRequestResponse.getResponse()) if self._log.get(i)._unauthorizedRequestResponse != None else 0, self._log.get(i)._enfocementStatus, self._log.get(i)._enfocementStatusUnauthorized) else: if (enforcementStatusFilter == self._log.get(i)._enfocementStatus) or (enforcementStatusFilter == self._log.get(i)._enfocementStatusUnauthorized): csvContent += "%d\t%s\t%d\t%d\t%d\t%s\t%s\n" % (self._log.get(i)._id,self._log.get(i)._url, len(self._log.get(i)._originalrequestResponse.getResponse()) if self._log.get(i)._originalrequestResponse != None else 0, len(self._log.get(i)._requestResponse.getResponse()) if self._log.get(i)._requestResponse != None else 0, len(self._log.get(i)._unauthorizedRequestResponse.getResponse()) if self._log.get(i)._unauthorizedRequestResponse != None else 0, self._log.get(i)._enfocementStatus, self._log.get(i)._enfocementStatusUnauthorized) f = open(fileToSave.getAbsolutePath(), 'w') f.writelines(csvContent) f.close() def exportToHTML(self): parentFrame = JFrame() fileChooser = JFileChooser() fileChooser.setSelectedFile(File("AutorizeReprort.html")); fileChooser.setDialogTitle("Save Autorize Report") userSelection = fileChooser.showSaveDialog(parentFrame) if userSelection == JFileChooser.APPROVE_OPTION: fileToSave = fileChooser.getSelectedFile() enforcementStatusFilter = self.exportES.getSelectedItem() htmlContent = """<html><title>Autorize Report by Barak Tawily</title> <style> .datagrid table { border-collapse: collapse; text-align: left; width: 100%; } .datagrid {font: normal 12px/150% Arial, Helvetica, sans-serif; background: #fff; overflow: hidden; border: 1px solid #006699; -webkit-border-radius: 3px; -moz-border-radius: 3px; border-radius: 3px; } .datagrid table td, .datagrid table th { padding: 3px 10px; } .datagrid table thead th {background:-webkit-gradient( linear, left top, left bottom, color-stop(0.05, #006699), color-stop(1, #00557F) );background:-moz-linear-gradient( center top, #006699 5%, #00557F 100% );filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#006699', endColorstr='#00557F');background-color:#006699; color:#FFFFFF; font-size: 15px; font-weight: bold; border-left: 1px solid #0070A8; } .datagrid table thead th:first-child { border: none; }.datagrid table tbody td { color: #00496B; border-left: 1px solid #E1EEF4;font-size: 12px;font-weight: normal; }.datagrid table tbody .alt td { background: #E1EEF4; color: #00496B; }.datagrid table tbody td:first-child { border-left: none; }.datagrid table tbody tr:last-child td { border-bottom: none; }.datagrid table tfoot td div { border-top: 1px solid #006699;background: #E1EEF4;} .datagrid table tfoot td { padding: 0; font-size: 12px } .datagrid table tfoot td div{ padding: 2px; }.datagrid table tfoot td ul { margin: 0; padding:0; list-style: none; text-align: right; }.datagrid table tfoot li { display: inline; }.datagrid table tfoot li a { text-decoration: none; display: inline-block; padding: 2px 8px; margin: 1px;color: #FFFFFF;border: 1px solid #006699;-webkit-border-radius: 3px; -moz-border-radius: 3px; border-radius: 3px; background:-webkit-gradient( linear, left top, left bottom, color-stop(0.05, #006699), color-stop(1, #00557F) );background:-moz-linear-gradient( center top, #006699 5%, #00557F 100% );filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#006699', endColorstr='#00557F');background-color:#006699; }.datagrid table tfoot ul.active, .datagrid table tfoot ul a:hover { text-decoration: none;border-color: #006699; color: #FFFFFF; background: none; background-color:#00557F;}div.dhtmlx_window_active, div.dhx_modal_cover_dv { position: fixed !important; } table { width: 100%; table-layout: fixed; } td { border: 1px solid #35f; overflow: hidden; text-overflow: ellipsis; } td.a { width: 13%; white-space: nowrap; } td.b { width: 9%; word-wrap: break-word; } </style> <body> <h1>Autorize Report<h1> <div class="datagrid"><table> <thead><tr><th width=\"3%\">ID</th><th width=\"48%\">URL</th><th width=\"9%\">Original length</th><th width=\"9%\">Modified length</th><th width=\"9%\">Unauthorized length</th><th width=\"11%\">Authorization Enforcement Status</th><th width=\"11%\">Authorization Unauthenticated Status</th></tr></thead> <tbody>""" for i in range(0,self._log.size()): color_modified = "" if self._log.get(i)._enfocementStatus == self._enfocementStatuses[0]: color_modified = "red" if self._log.get(i)._enfocementStatus == self._enfocementStatuses[1]: color_modified = "yellow" if self._log.get(i)._enfocementStatus == self._enfocementStatuses[2]: color_modified = "LawnGreen" color_unauthorized = "" if self._log.get(i)._enfocementStatusUnauthorized == self._enfocementStatuses[0]: color_unauthorized = "red" if self._log.get(i)._enfocementStatusUnauthorized == self._enfocementStatuses[1]: color_unauthorized = "yellow" if self._log.get(i)._enfocementStatusUnauthorized == self._enfocementStatuses[2]: color_unauthorized = "LawnGreen" if enforcementStatusFilter == "All Statuses": htmlContent += "<tr><td>%d</td><td><a href=\"%s\">%s</a></td><td>%d</td><td>%d</td><td>%d</td><td bgcolor=\"%s\">%s</td><td bgcolor=\"%s\">%s</td></tr>" % (self._log.get(i)._id,self._log.get(i)._url,self._log.get(i)._url, len(self._log.get(i)._originalrequestResponse.getResponse()) if self._log.get(i)._originalrequestResponse != None else 0, len(self._log.get(i)._requestResponse.getResponse()) if self._log.get(i)._requestResponse != None else 0, len(self._log.get(i)._unauthorizedRequestResponse.getResponse()) if self._log.get(i)._unauthorizedRequestResponse != None else 0, color_modified, self._log.get(i)._enfocementStatus, color_unauthorized, self._log.get(i)._enfocementStatusUnauthorized) else: if (enforcementStatusFilter == self._log.get(i)._enfocementStatus) or (enforcementStatusFilter == self._log.get(i)._enfocementStatusUnauthorized): htmlContent += "<tr><td>%d</td><td><a href=\"%s\">%s</a></td><td>%d</td><td>%d</td><td>%d</td><td bgcolor=\"%s\">%s</td><td bgcolor=\"%s\">%s</td></tr>" % (self._log.get(i)._id,self._log.get(i)._url,self._log.get(i)._url, len(self._log.get(i)._originalrequestResponse.getResponse()) if self._log.get(i)._originalrequestResponse != None else 0, len(self._log.get(i)._requestResponse.getResponse()) if self._log.get(i)._requestResponse != None else 0, len(self._log.get(i)._unauthorizedRequestResponse.getResponse()) if self._log.get(i)._unauthorizedRequestResponse != None else 0, color_modified, self._log.get(i)._enfocementStatus, color_unauthorized, self._log.get(i)._enfocementStatusUnauthorized) htmlContent += "</tbody></table></div></body></html>" f = open(fileToSave.getAbsolutePath(), 'w') f.writelines(htmlContent) f.close() # # implement IContextMenuFactory # def createMenuItems(self, invocation): responses = invocation.getSelectedMessages(); if responses > 0: ret = LinkedList() requestMenuItem = JMenuItem("Send request to Autorize"); cookieMenuItem = JMenuItem("Send cookie to Autorize"); requestMenuItem.addActionListener(handleMenuItems(self,responses[0], "request")) cookieMenuItem.addActionListener(handleMenuItems(self, responses[0], "cookie")) ret.add(requestMenuItem); ret.add(cookieMenuItem); return(ret); return null; # # implement ITab # def getTabCaption(self): return "Autorize" def getUiComponent(self): return self._splitpane # # extend AbstractTableModel # def getRowCount(self): try: return self._log.size() except: return 0 def getColumnCount(self): return 7 def getColumnName(self, columnIndex): if columnIndex == 0: return "ID" if columnIndex == 1: return "URL" if columnIndex == 2: return "Orig. Length" if columnIndex == 3: return "Modif. Length" if columnIndex == 4: return "Unauth. Length" if columnIndex == 5: return "Authorization Enforcement Status" if columnIndex == 6: return "Authorization Unauth. Status" return "" def getColumnClass(self, columnIndex): if columnIndex == 0: return Integer if columnIndex == 1: return String if columnIndex == 2: return Integer if columnIndex == 3: return Integer if columnIndex == 4: return Integer if columnIndex == 5: return String if columnIndex == 6: return String return String def getValueAt(self, rowIndex, columnIndex): logEntry = self._log.get(rowIndex) if columnIndex == 0: return logEntry._id if columnIndex == 1: return logEntry._url.toString() if columnIndex == 2: return len(logEntry._originalrequestResponse.getResponse()) if columnIndex == 3: return len(logEntry._requestResponse.getResponse()) if columnIndex == 4: if logEntry._unauthorizedRequestResponse != None: return len(logEntry._unauthorizedRequestResponse.getResponse()) else: #return "-" return 0 if columnIndex == 5: return logEntry._enfocementStatus if columnIndex == 6: return logEntry._enfocementStatusUnauthorized return "" # # implement IMessageEditorController # this allows our request/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() # # implement IHttpListener # def processHttpMessage(self, toolFlag, messageIsRequest, messageInfo): #if (self.intercept == 1) and (toolFlag != self._callbacks.TOOL_EXTENDER): if (self.intercept == 1) and (toolFlag == self._callbacks.TOOL_PROXY): if self.prevent304.isSelected(): if messageIsRequest: requestHeaders = list(self._helpers.analyzeRequest(messageInfo).getHeaders()) newHeaders = list() found = 0 for header in requestHeaders: if not "If-None-Match:" in header and not "If-Modified-Since:" in header: newHeaders.append(header) found = 1 if found == 1: requestInfo = self._helpers.analyzeRequest(messageInfo) bodyBytes = messageInfo.getRequest()[requestInfo.getBodyOffset():] bodyStr = self._helpers.bytesToString(bodyBytes) messageInfo.setRequest(self._helpers.buildHttpMessage(newHeaders, bodyStr)) if not messageIsRequest: if not self.replaceString.getText() in self._helpers.analyzeRequest(messageInfo).getHeaders(): if self.ignore304.isSelected(): firstHeader = self._helpers.analyzeResponse(messageInfo.getResponse()).getHeaders()[0] if "304" in firstHeader or "204" in firstHeader: return if self.IFList.getModel().getSize() == 0: self.checkAuthorization(messageInfo,self._helpers.analyzeResponse(messageInfo.getResponse()).getHeaders(),self.doUnauthorizedRequest.isSelected()) else: urlString = str(self._helpers.analyzeRequest(messageInfo).getUrl()) do_the_check = 1 for i in range(0,self.IFList.getModel().getSize()): if self.IFList.getModel().getElementAt(i).split(":")[0] == "Scope items only": currentURL = URL(urlString) if not self._callbacks.isInScope(currentURL): do_the_check = 0 if self.IFList.getModel().getElementAt(i).split(":")[0] == "URL Contains (simple string)": if self.IFList.getModel().getElementAt(i)[30:] not in urlString: do_the_check = 0 if self.IFList.getModel().getElementAt(i).split(":")[0] == "URL Contains (regex)": regex_string = self.IFList.getModel().getElementAt(i)[22:] p = re.compile(regex_string, re.IGNORECASE) if not p.search(urlString): do_the_check = 0 if self.IFList.getModel().getElementAt(i).split(":")[0] == "URL Not Contains (simple string)": if self.IFList.getModel().getElementAt(i)[34:] in urlString: do_the_check = 0 if self.IFList.getModel().getElementAt(i).split(":")[0] == "URL Not Contains (regex)": regex_string = self.IFList.getModel().getElementAt(i)[26:] p = re.compile(regex_string, re.IGNORECASE) if p.search(urlString): do_the_check = 0 if do_the_check: self.checkAuthorization(messageInfo,self._helpers.analyzeResponse(messageInfo.getResponse()).getHeaders(),self.doUnauthorizedRequest.isSelected()) return def sendRequestToAutorizeWork(self,messageInfo): if messageInfo.getResponse() == None: message = self.makeMessage(messageInfo,False,False) requestResponse = self.makeRequest(messageInfo, message) self.checkAuthorization(requestResponse,self._helpers.analyzeResponse(requestResponse.getResponse()).getHeaders(),self.doUnauthorizedRequest.isSelected()) else: self.checkAuthorization(messageInfo,self._helpers.analyzeResponse(messageInfo.getResponse()).getHeaders(),self.doUnauthorizedRequest.isSelected()) def makeRequest(self, messageInfo, message): requestURL = self._helpers.analyzeRequest(messageInfo).getUrl() return self._callbacks.makeHttpRequest(self._helpers.buildHttpService(str(requestURL.getHost()), int(requestURL.getPort()), requestURL.getProtocol() == "https"), message) def makeMessage(self, messageInfo, removeOrNot, authorizeOrNot): requestInfo = self._helpers.analyzeRequest(messageInfo) headers = requestInfo.getHeaders() if removeOrNot: headers = list(headers) removeHeaders = ArrayList() removeHeaders.add(self.replaceString.getText()[0:self.replaceString.getText().index(":")]) for header in headers[:]: for removeHeader in removeHeaders: if removeHeader in header: headers.remove(header) if authorizeOrNot: headers.append(self.replaceString.getText()) msgBody = messageInfo.getRequest()[requestInfo.getBodyOffset():] return self._helpers.buildHttpMessage(headers, msgBody) def checkBypass(self,oldStatusCode,newStatusCode,oldContentLen,newContentLen,filters,requestResponse): analyzedResponse = self._helpers.analyzeResponse(requestResponse.getResponse()) impression = "" if oldStatusCode == newStatusCode: if oldContentLen == newContentLen: impression = self._enfocementStatuses[0] else: auth_enforced = 1 for filter in filters: if str(filter).startswith("Headers (simple string): "): if not(filter[25:] in self._helpers.bytesToString(requestResponse.getResponse()[0:analyzedResponse.getBodyOffset()])): auth_enforced = 0 if str(filter).startswith("Headers (regex): "): regex_string = filter[17:] p = re.compile(regex_string, re.IGNORECASE) if not p.search(self._helpers.bytesToString(requestResponse.getResponse()[0:analyzedResponse.getBodyOffset()])): auth_enforced = 0 if str(filter).startswith("Body (simple string): "): if not(filter[22:] in self._helpers.bytesToString(requestResponse.getResponse()[analyzedResponse.getBodyOffset():])): auth_enforced = 0 if str(filter).startswith("Body (regex): "): regex_string = filter[14:] p = re.compile(regex_string, re.IGNORECASE) if not p.search(self._helpers.bytesToString(requestResponse.getResponse()[analyzedResponse.getBodyOffset():])): auth_enforced = 0 if str(filter).startswith("Full request (simple string): "): if not(filter[30:] in self._helpers.bytesToString(requestResponse.getResponse())): auth_enforced = 0 if str(filter).startswith("Full request (regex): "): regex_string = filter[22:] p = re.compile(regex_string, re.IGNORECASE) if not p.search(self._helpers.bytesToString(requestResponse.getResponse())): auth_enforced = 0 if str(filter).startswith("Content-Length: "): if newContentLen != filter: auth_enforced = 0 if auth_enforced: impression = self._enfocementStatuses[2] else: impression = self._enfocementStatuses[1] else: impression = self._enfocementStatuses[2] return impression def checkAuthorization(self, messageInfo, originalHeaders, checkUnauthorized): message = self.makeMessage(messageInfo,True,True) requestResponse = self.makeRequest(messageInfo, message) analyzedResponse = self._helpers.analyzeResponse(requestResponse.getResponse()) oldStatusCode = originalHeaders[0] newStatusCode = analyzedResponse.getHeaders()[0] oldContentLen = self.getContentLength(originalHeaders) newContentLen = self.getContentLength(analyzedResponse.getHeaders()) # Check unauthorized request if checkUnauthorized: messageUnauthorized = self.makeMessage(messageInfo,True,False) requestResponseUnauthorized = self.makeRequest(messageInfo, messageUnauthorized) analyzedResponseUnauthorized = self._helpers.analyzeResponse(requestResponseUnauthorized.getResponse()) statusCodeUnauthorized = analyzedResponseUnauthorized.getHeaders()[0] contentLenUnauthorized = self.getContentLength(analyzedResponseUnauthorized.getHeaders()) EDFilters = self.EDModel.toArray() impression = self.checkBypass(oldStatusCode,newStatusCode,oldContentLen,newContentLen,EDFilters,requestResponse) if checkUnauthorized: EDFiltersUnauth = self.EDModelUnauth.toArray() impressionUnauthorized = self.checkBypass(oldStatusCode,statusCodeUnauthorized,oldContentLen,contentLenUnauthorized,EDFiltersUnauth,requestResponseUnauthorized) self._lock.acquire() row = self._log.size() if checkUnauthorized: self._log.add(LogEntry(self.currentRequestNumber,self._callbacks.saveBuffersToTempFiles(requestResponse), self._helpers.analyzeRequest(requestResponse).getUrl(),messageInfo,impression,self._callbacks.saveBuffersToTempFiles(requestResponseUnauthorized),impressionUnauthorized)) # same requests not include again. else: self._log.add(LogEntry(self.currentRequestNumber,self._callbacks.saveBuffersToTempFiles(requestResponse), self._helpers.analyzeRequest(requestResponse).getUrl(),messageInfo,impression,None,"Disabled")) # same requests not include again. self.fireTableRowsInserted(row, row) self.currentRequestNumber = self.currentRequestNumber + 1 self._lock.release() def getContentLength(self, analyzedResponseHeaders): for header in analyzedResponseHeaders: if "Content-Length:" in header: return header; return "null" def getCookieFromMessage(self, messageInfo): headers = list(self._helpers.analyzeRequest(messageInfo.getRequest()).getHeaders()) for header in headers: if "Cookie:" in header: return header return None
def __init__(self): super(WorkHelper, self).__init__() self.clipboard = Toolkit.getDefaultToolkit().getSystemClipboard() ############################################################# # Layout: layout = GroupLayout(self.getContentPane()) self.getContentPane().setLayout(layout) layout.setAutoCreateGaps(True) layout.setAutoCreateContainerGaps(True) ############################################################# ############################################################# # Frame Area: Larea1 = JLabel("InputArea:") Sarea1 = JScrollPane() self.area1 = JTextArea() self.area1.setToolTipText("Input Area") self.area1.setEditable(True) self.area1.setBorder(BorderFactory.createLineBorder(Color.gray)) Sarea1.setPreferredSize(Dimension(300,100)) Sarea1.getViewport().setView((self.area1)) bClear = JButton("Clear", actionPerformed=self.bClear) bClear.setToolTipText("Clears the text form both Input and Output text Areas") bCopyToInput = JButton("Copy to Input", actionPerformed=self.bCopyToInput) bCopyToInput.setToolTipText("Copy the text from the Output Area to the Input Area for further Operations") self.cCtClipB = JCheckBox("Auto-Copy"); self.cCtClipB.setToolTipText("When 'Checked' after the Categories are created they will added to the clipboard") self.cCtClipB.setSelected(1) Larea2 = JLabel("OutputArea:") Sarea2 = JScrollPane() self.area2 = JTextArea() self.area2.setToolTipText("Output Area") self.area2.setEditable(False) self.area2.setBorder(BorderFactory.createLineBorder(Color.gray)) Sarea2.setPreferredSize(Dimension(300,100)) Sarea2.getViewport().setView((self.area2)) ############################################################# # Tabbed Area: tabPane = JTabbedPane(JTabbedPane.TOP) self.getContentPane().add(tabPane) ##################################################### # Text Edit pane panel_TEdit = JPanel() layout2 = GroupLayout(panel_TEdit) layout2.setAutoCreateGaps(True) layout2.setAutoCreateContainerGaps(True) panel_TEdit.setLayout(layout2) bRemoveNBSP_L = JButton("Clean LText", actionPerformed=self.bRemoveNBSP_L) bRemoveNBSP_L.setToolTipText("Removes Spaces, Tabs from the start of every text line from the input Area") bRemoveNBSP_R = JButton("Clean RText", actionPerformed=self.bRemoveNBSP_R) bRemoveNBSP_R.setToolTipText("Removes Spaces, Tabs from the end of every text line from the input Area") self.ReplaceThis = JTextField() self.ReplaceThis = JTextField(maximumSize=Dimension(120,25)) self.ReplaceThis.setToolTipText("Text to be replaced") self.ReplaceThat = JTextField() self.ReplaceThat = JTextField(maximumSize=Dimension(120,25)) self.ReplaceThat.setToolTipText("Text to be placed") bSandReplace = JButton("Replace Text", actionPerformed=self.bSandReplace) bSandReplace.setToolTipText("Replace the text from This with Text from That in the Text from the Input Area and displays it in the Output Area") bRemNumbers = JButton("Rem Numbers", actionPerformed=self.RemNumbers) bRemNumbers.setToolTipText("Removes numbers from the start of every line") ##################################################### # Dimension pane panel_Dimensions = JPanel() layout3 = GroupLayout(panel_Dimensions) layout3.setAutoCreateGaps(True) layout3.setAutoCreateContainerGaps(True) panel_Dimensions.setLayout(layout3) self.cCurly = JCheckBox("Curly"); self.cCurly.setToolTipText("When 'Checked' Curly Brackets will surround the Categories") self.cCurly.setSelected(1) self.cSemiC = JCheckBox("SemiColumn"); self.cSemiC.setToolTipText("When 'Checked' after the Categories are created at the end will be a semicolomn") self.cSemiC.setSelected(1) self.iStart = JTextField(maximumSize=Dimension(40,25)) self.iStart.setToolTipText("The Start Index for the Making of the Categories") self.RThis = JTextField() self.RThis = JTextField(maximumSize=Dimension(120,25)) self.RThis.setToolTipText("The Starting Index used in creating the Categorical") self.RThat = JTextField() self.RThat = JTextField(maximumSize=Dimension(120,25)) self.RThat.setToolTipText("The Finish Index used in creating the Categorical") optioncCategories = JLabel("Options:") bcCat = JButton("CreatCateg", actionPerformed=self.bcCat) bcCat.setToolTipText("Create a categorical form starting C_Index to finish C_Index; Use the text boxes to define the indexes") bM_Categories = JButton("Categories", actionPerformed=self.mCategories) bM_Categories.setToolTipText("Make Categories using the lines from the Input Area. Use it to define Categorical questions.") ##################################################### # ConfirmIt pane panel_ConfirmIt = JPanel() layout4 = GroupLayout(panel_ConfirmIt) layout4.setAutoCreateGaps(True) layout4.setAutoCreateContainerGaps(True) panel_ConfirmIt.setLayout(layout4) self.PID = JTextField() self.PID = JTextField(maximumSize=Dimension(120,25)) self.PID.setToolTipText("The PID number used for creating links with PID and ids from every line of the Input Area") bClinks = JButton("Create Links", actionPerformed=self.bClinks) bClinks.setToolTipText("Create links for a project using PID and ID, ID`s are read from every line of the Input Area") bClinksNA = JButton("Create Links NA ", actionPerformed=self.bClinksNA) bClinksNA.setToolTipText("Create links for a project using PID and ID`s from the standard sample test for US") bClinksCA = JButton("Create Links CA", actionPerformed=self.bClinksCA) bClinksCA.setToolTipText("Create links for a project using PID and ID`s from the standard sample test for CA") self.Width = JTextField() self.Width = JTextField(maximumSize=Dimension(120,25)) self.Width.setToolTipText("The Width used in creating the DIV html tag, note the dimension used is in px") baddDIVt = JButton("Add DIV tag", actionPerformed=self.baddDIVt) baddDIVt.setToolTipText("Create a DIV tag for every line in the Input Area") ##################################################### # Statistics pane panel_Statistics = JPanel() layout5 = GroupLayout(panel_Statistics) layout5.setAutoCreateGaps(True) layout5.setAutoCreateContainerGaps(True) panel_Statistics.setLayout(layout5) ##################################################### # TimeTraking pane panel_TimeTraking = JPanel() layout6 = GroupLayout(panel_TimeTraking) layout6.setAutoCreateGaps(True) layout6.setAutoCreateContainerGaps(True) panel_TimeTraking.setLayout(layout6) ##################################################### # Tabbed Area Tabs tabPane.addTab("Text Edit", panel_TEdit) tabPane.addTab("Dimensions", panel_Dimensions) tabPane.addTab("ConfirmIt", panel_ConfirmIt) tabPane.addTab("Statistics", panel_Statistics) tabPane.addTab("TimeTraking", panel_TimeTraking) ############################################################# ############################################################# # Aplication Layouts: 2 groups one Horizontal and one Vertical ############################################################# # Frame Layout: 2 groups one Horizontal and one Vertical layout.setHorizontalGroup(layout.createSequentialGroup() .addGroup(layout.createParallelGroup() .addComponent(Larea1) .addComponent(Sarea1) .addComponent(Sarea2) .addGroup(layout.createSequentialGroup() .addComponent(bCopyToInput) .addComponent(bClear) .addComponent(self.cCtClipB)) .addComponent(Larea2)) .addGroup(layout.createParallelGroup() .addComponent(tabPane)) ) layout.setVerticalGroup(layout.createSequentialGroup() .addGroup(layout.createParallelGroup() .addGroup(layout.createSequentialGroup() .addComponent(Larea1) .addComponent(Sarea1) .addGroup(layout.createParallelGroup() .addComponent(bCopyToInput) .addComponent(bClear) .addComponent(self.cCtClipB) ) .addComponent(Larea2) .addComponent(Sarea2)) .addGroup(layout.createSequentialGroup() .addComponent(tabPane)) ) ) ############################################################# # TEdit Layout: 2 groups one Horizontal and one Vertical layout2.setHorizontalGroup(layout2.createSequentialGroup() .addGroup(layout2.createParallelGroup() .addGroup(layout2.createSequentialGroup() .addComponent(bRemNumbers) .addComponent(bRemoveNBSP_L) .addComponent(bRemoveNBSP_R)) .addGroup(layout2.createSequentialGroup() .addComponent(bSandReplace) .addComponent(self.ReplaceThis) .addComponent(self.ReplaceThat)) )) layout2.setVerticalGroup(layout2.createSequentialGroup() .addGroup(layout2.createParallelGroup() .addComponent(bRemNumbers) .addComponent(bRemoveNBSP_L) .addComponent(bRemoveNBSP_R)) .addGroup(layout2.createParallelGroup() .addComponent(bSandReplace) .addComponent(self.ReplaceThis) .addComponent(self.ReplaceThat)) ) ############################################################# # Dimensions Layout: 2 groups one Horizontal and one Vertical layout3.setHorizontalGroup(layout3.createSequentialGroup() .addGroup(layout3.createParallelGroup() .addGroup(layout3.createSequentialGroup() .addComponent(bM_Categories) .addComponent(self.iStart)) .addGroup(layout3.createSequentialGroup() .addComponent(optioncCategories) .addComponent(self.cCurly) .addComponent(self.cSemiC) ) .addGroup(layout3.createSequentialGroup() .addComponent(bcCat) .addComponent(self.RThis) .addComponent(self.RThat)) .addGroup(layout3.createSequentialGroup() ) ) ) layout3.setVerticalGroup(layout3.createSequentialGroup() .addGroup(layout3.createSequentialGroup() .addGroup(layout3.createParallelGroup() .addComponent(bM_Categories) .addComponent(self.iStart)) .addGroup(layout3.createParallelGroup() .addComponent(bcCat) .addComponent(self.RThis) .addComponent(self.RThat)) .addGroup(layout3.createParallelGroup() .addGroup(layout3.createParallelGroup() .addComponent(optioncCategories) .addComponent(self.cCurly) .addComponent(self.cSemiC) ) ) ) ) ############################################################# # ConfimIT Layout: 2 groups one Horizontal and one Vertical layout4.setHorizontalGroup(layout4.createSequentialGroup() .addGroup(layout4.createParallelGroup() .addGroup(layout4.createSequentialGroup() .addComponent(bClinks) .addComponent(self.PID) ) .addGroup(layout4.createSequentialGroup() .addComponent(bClinksNA) .addComponent(bClinksCA) ) .addGroup(layout4.createSequentialGroup() .addComponent(baddDIVt) .addComponent(self.Width) ) )) layout4.setVerticalGroup(layout4.createSequentialGroup() .addGroup(layout4.createSequentialGroup() .addGroup(layout4.createParallelGroup() .addComponent(bClinks) .addComponent(self.PID)) .addGroup(layout4.createParallelGroup() .addComponent(bClinksNA) .addComponent(bClinksCA) ) .addGroup(layout4.createParallelGroup() .addComponent(baddDIVt) .addComponent(self.Width) ) )) #layout2.linkSize(SwingConstants.HORIZONTAL, [self.cCurly,bM_Categories]) #layout.linkSize(SwingConstants.HORIZONTAL, [ok, bCopyToInput, close, bM_Categories]) #layout3.linkSize(SwingConstants.HORIZONTAL, [self.RThis,self.RThat,bRemoveNBSP_L,bRemoveNBSP_R,bM_Categories,bSandReplace,bcCat]) ############################################################# ############################################################# # Aplication Settings self.pack() #self.setPreferredSize(Dimension(1000, 1000)) self.setTitle("Workhelper") self.setSize(800, 500) self.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE) self.setLocationRelativeTo(None) self.setVisible(True)
def registerExtenderCallbacks(self, callbacks): # Initialize the global stdout stream global stdout # Keep a reference to our callbacks object self._callbacks = callbacks # Obtain an extension helpers object self._helpers = callbacks.getHelpers() # set our extension name callbacks.setExtensionName("Burpsuite Yara Scanner") # Create the log and a lock on which to synchronize when adding log entries self._log = ArrayList() self._lock = Lock() # main split pane splitpane = JSplitPane(JSplitPane.VERTICAL_SPLIT) # table of log entries logTable = Table(self) scrollPane = JScrollPane(logTable) splitpane.setLeftComponent(scrollPane) # Options panel optionsPanel = JPanel() optionsPanel.setLayout(GridBagLayout()) constraints = GridBagConstraints() yara_exe_label = JLabel("Yara Executable Location:") constraints.fill = GridBagConstraints.HORIZONTAL constraints.gridx = 0 constraints.gridy = 0 optionsPanel.add(yara_exe_label, constraints) self._yara_exe_txtField = JTextField(25) constraints.fill = GridBagConstraints.HORIZONTAL constraints.gridx = 1 constraints.gridy = 0 optionsPanel.add(self._yara_exe_txtField, constraints) yara_rules_label = JLabel("Yara Rules File:") constraints.fill = GridBagConstraints.HORIZONTAL constraints.gridx = 0 constraints.gridy = 1 optionsPanel.add(yara_rules_label, constraints) self._yara_rules_files = Vector() self._yara_rules_files.add("< None >") self._yara_rules_fileList = JList(self._yara_rules_files) constraints.fill = GridBagConstraints.HORIZONTAL constraints.gridx = 1 constraints.gridy = 1 optionsPanel.add(self._yara_rules_fileList, constraints) self._yara_rules_select_files_button = JButton("Select Files") self._yara_rules_select_files_button.addActionListener(self) constraints.fill = GridBagConstraints.HORIZONTAL constraints.gridx = 1 constraints.gridy = 2 optionsPanel.add(self._yara_rules_select_files_button, constraints) self._yara_clear_button = JButton("Clear Yara Results Table") self._yara_clear_button.addActionListener(self) constraints.fill = GridBagConstraints.HORIZONTAL constraints.gridx = 1 constraints.gridy = 3 optionsPanel.add(self._yara_clear_button, constraints) # Tabs with request/response viewers viewerTabs = JTabbedPane() self._requestViewer = callbacks.createMessageEditor(self, False) self._responseViewer = callbacks.createMessageEditor(self, False) viewerTabs.addTab("Request", self._requestViewer.getComponent()) viewerTabs.addTab("Response", self._responseViewer.getComponent()) splitpane.setRightComponent(viewerTabs) # Tabs for the Yara output and the Options self._mainTabs = JTabbedPane() self._mainTabs.addTab("Yara Output", splitpane) self._mainTabs.addTab("Options", optionsPanel) # customize our UI components callbacks.customizeUiComponent(splitpane) callbacks.customizeUiComponent(logTable) callbacks.customizeUiComponent(scrollPane) callbacks.customizeUiComponent(viewerTabs) callbacks.customizeUiComponent(self._mainTabs) # add the custom tab to Burp's UI callbacks.addSuiteTab(self) # add ourselves as a context menu factory callbacks.registerContextMenuFactory(self) # Custom Menu Item self.menuItem = JMenuItem("Scan with Yara") self.menuItem.addActionListener(self) # obtain our output stream stdout = PrintWriter(callbacks.getStdout(), True) # Print a startup notification stdout.println("Burpsuite Yara scanner initialized.")
def registerExtenderCallbacks(self, callbacks): # keep a reference to our callbacks object self._callbacks = callbacks # obtain an extension helpers object self._helpers = callbacks.getHelpers() # set our extension name callbacks.setExtensionName("Otter") # create the log and a lock on which to synchronize when adding log entries self._log = ArrayList() self._lock = Lock() # main split pane for log entries and request/response viewing self._settingPanel = JPanel() self._logPane = JSplitPane(JSplitPane.VERTICAL_SPLIT) # setup settings pane ui self._settingPanel.setBounds(0,0,1000,1000) self._settingPanel.setLayout(None) self._isRegexp = JCheckBox("Use regexp for matching.") self._isRegexp.setBounds(10, 10, 220, 20) matchLabel = JLabel("String to Match:") matchLabel.setBounds(10, 40, 200, 20) self._matchString = JTextArea("User 1 Session Information") self._matchString.setWrapStyleWord(True) self._matchString.setLineWrap(True) matchString = JScrollPane(self._matchString) matchString.setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_AS_NEEDED) matchString.setBounds(10, 60, 400, 200) replaceLabel = JLabel("String to Replace:") replaceLabel.setBounds(10, 270, 200, 20) self._replaceString = JTextArea("User 2 Session Information") self._replaceString.setWrapStyleWord(True) self._replaceString.setLineWrap(True) replaceString = JScrollPane(self._replaceString) replaceString.setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_AS_NEEDED) replaceString.setBounds(10, 290, 400, 200) self._settingPanel.add(self._isRegexp) self._settingPanel.add(matchLabel) self._settingPanel.add(matchString) self._settingPanel.add(replaceLabel) self._settingPanel.add(replaceString) # table of log entries logTable = Table(self) logTable.getColumnModel().getColumn(0).setPreferredWidth(700) logTable.getColumnModel().getColumn(1).setPreferredWidth(150) logTable.getColumnModel().getColumn(2).setPreferredWidth(100) logTable.getColumnModel().getColumn(3).setPreferredWidth(130) logTable.getColumnModel().getColumn(4).setPreferredWidth(100) logTable.getColumnModel().getColumn(5).setPreferredWidth(130) scrollPane = JScrollPane(logTable) self._logPane.setLeftComponent(scrollPane) # tabs with request/response viewers logTabs = JTabbedPane() self._origRequestViewer = callbacks.createMessageEditor(self, False) self._origResponseViewer = callbacks.createMessageEditor(self, False) self._modRequestViewer = callbacks.createMessageEditor(self, False) self._modResponseViewer = callbacks.createMessageEditor(self, False) logTabs.addTab("Original Request", self._origRequestViewer.getComponent()) logTabs.addTab("Original Response", self._origResponseViewer.getComponent()) logTabs.addTab("Modified Request", self._modRequestViewer.getComponent()) logTabs.addTab("Modified Response", self._modResponseViewer.getComponent()) self._logPane.setRightComponent(logTabs) # top most tab interface that seperates log entries from settings maintabs = JTabbedPane() maintabs.addTab("Log Entries", self._logPane) maintabs.addTab("Settings", self._settingPanel) self._maintabs = maintabs # customize the UI components callbacks.customizeUiComponent(maintabs) # add the custom tab to Burp's UI callbacks.addSuiteTab(self) # register ourselves as an HTTP listener callbacks.registerHttpListener(self) return
class QatDialog(ToggleDialog): """ToggleDialog for error type selection and buttons for reviewing errors in sequence """ def __init__(self, name, iconName, tooltip, shortcut, height, app): ToggleDialog.__init__(self, name, iconName, tooltip, shortcut, height) self.app = app tools = app.tools #Main panel of the dialog mainPnl = JPanel(BorderLayout()) mainPnl.setBorder(BorderFactory.createEmptyBorder(0, 1, 1, 1)) ### First tab: errors selection and download ########################### #ComboBox with tools names self.toolsComboModel = DefaultComboBoxModel() for tool in tools: self.add_data_to_models(tool) self.toolsCombo = JComboBox(self.toolsComboModel, actionListener=ToolsComboListener(app)) renderer = ToolsComboRenderer(self.app) renderer.setPreferredSize(Dimension(20, 20)) self.toolsCombo.setRenderer(renderer) self.toolsCombo.setToolTipText(app.strings.getString("Select_a_quality_assurance_tool")) #ComboBox with categories names ("views"), of the selected tool self.viewsCombo = JComboBox(actionListener=ViewsComboListener(app)) self.viewsCombo.setToolTipText(app.strings.getString("Select_a_category_of_error")) #Popup for checks table self.checkPopup = JPopupMenu() #add favourite check self.menuItemAdd = JMenuItem(self.app.strings.getString("Add_to_favourites")) self.menuItemAdd.setIcon(ImageIcon(File.separator.join([self.app.SCRIPTDIR, "tools", "data", "Favourites", "icons", "tool_16.png"]))) self.menuItemAdd.addActionListener(PopupActionListener(self.app)) self.checkPopup.add(self.menuItemAdd) #remove favourite check self.menuItemRemove = JMenuItem(self.app.strings.getString("Remove_from_favourites")) self.menuItemRemove.setIcon(ImageIcon(File.separator.join([self.app.SCRIPTDIR, "tools", "data", "Favourites", "icons", "black_tool_16.png"]))) self.menuItemRemove.addActionListener(PopupActionListener(self.app)) self.checkPopup.add(self.menuItemRemove) #Help link for selected check self.menuItemHelp = JMenuItem(self.app.strings.getString("check_help")) self.menuItemHelp.setIcon(ImageIcon(File.separator.join([self.app.SCRIPTDIR, "images", "icons", "info_16.png"]))) self.checkPopup.add(self.menuItemHelp) self.menuItemHelp.addActionListener(PopupActionListener(self.app)) #Table with checks of selected tool and view self.checksTable = JTable() self.iconrenderer = IconRenderer() self.iconrenderer.setHorizontalAlignment(JLabel.CENTER) scrollPane = JScrollPane(self.checksTable) self.checksTable.setFillsViewportHeight(True) tableSelectionModel = self.checksTable.getSelectionModel() tableSelectionModel.addListSelectionListener(ChecksTableListener(app)) self.checksTable.addMouseListener(ChecksTableClickListener(app, self.checkPopup, self.checksTable)) #Favourite area status indicator self.favAreaIndicator = JLabel() self.update_favourite_zone_indicator() self.favAreaIndicator.addMouseListener(FavAreaIndicatorListener(app)) #label with OSM id of the object currently edited and number of #errors still to review self.checksTextFld = JTextField("", editable=0, border=None, background=None) #checks buttons btnsIconsDir = File.separator.join([app.SCRIPTDIR, "images", "icons"]) downloadIcon = ImageIcon(File.separator.join([btnsIconsDir, "download.png"])) self.downloadBtn = JButton(downloadIcon, actionPerformed=app.on_downloadBtn_clicked, enabled=0) startIcon = ImageIcon(File.separator.join([btnsIconsDir, "start_fixing.png"])) self.startBtn = JButton(startIcon, actionPerformed=app.on_startBtn_clicked, enabled=0) self.downloadBtn.setToolTipText(app.strings.getString("Download_errors_in_this_area")) self.startBtn.setToolTipText(app.strings.getString("Start_fixing_the_selected_errors")) #tab layout panel1 = JPanel(BorderLayout(0, 1)) comboboxesPnl = JPanel(GridLayout(0, 2, 5, 0)) comboboxesPnl.add(self.toolsCombo) comboboxesPnl.add(self.viewsCombo) checksPnl = JPanel(BorderLayout(0, 1)) checksPnl.add(scrollPane, BorderLayout.CENTER) self.statsPanel = JPanel(BorderLayout(4, 0)) self.statsPanel_def_color = self.statsPanel.getBackground() self.statsPanel.add(self.checksTextFld, BorderLayout.CENTER) self.statsPanel.add(self.favAreaIndicator, BorderLayout.LINE_START) checksPnl.add(self.statsPanel, BorderLayout.PAGE_END) checksButtonsPnl = JPanel(GridLayout(0, 2, 0, 0)) checksButtonsPnl.add(self.downloadBtn) checksButtonsPnl.add(self.startBtn) panel1.add(comboboxesPnl, BorderLayout.PAGE_START) panel1.add(checksPnl, BorderLayout.CENTER) panel1.add(checksButtonsPnl, BorderLayout.PAGE_END) ### Second tab: errors fixing ########################################## #label with error stats self.errorTextFld = JTextField("", editable=0, border=None, background=None) #label with current error description self.errorDesc = JLabel("") self.errorDesc.setAlignmentX(0.5) #error buttons errorInfoBtnIcon = ImageProvider.get("info") self.errorInfoBtn = JButton(errorInfoBtnIcon, actionPerformed=app.on_errorInfoBtn_clicked, enabled=0) notErrorIcon = ImageIcon(File.separator.join([btnsIconsDir, "not_error.png"])) self.notErrorBtn = JButton(notErrorIcon, actionPerformed=app.on_falsePositiveBtn_clicked, enabled=0) ignoreIcon = ImageIcon(File.separator.join([btnsIconsDir, "skip.png"])) self.ignoreBtn = JButton(ignoreIcon, actionPerformed=app.on_ignoreBtn_clicked, enabled=0) correctedIcon = ImageIcon(File.separator.join([btnsIconsDir, "corrected.png"])) self.correctedBtn = JButton(correctedIcon, actionPerformed=app.on_correctedBtn_clicked, enabled=0) nextIcon = ImageIcon(File.separator.join([btnsIconsDir, "next.png"])) self.nextBtn = JButton(nextIcon, actionPerformed=app.on_nextBtn_clicked, enabled=0) #self.nextBtn.setMnemonic(KeyEvent.VK_RIGHT) self.errorInfoBtn.setToolTipText(app.strings.getString("open_error_info_dialog")) self.notErrorBtn.setToolTipText(app.strings.getString("flag_false_positive")) self.ignoreBtn.setToolTipText(app.strings.getString("Skip_and_don't_show_me_this_error_again")) self.correctedBtn.setToolTipText(app.strings.getString("flag_corrected_error")) self.nextBtn.setToolTipText(app.strings.getString("Go_to_next_error")) #tab layout self.panel2 = JPanel(BorderLayout()) self.panel2.add(self.errorTextFld, BorderLayout.PAGE_START) self.panel2.add(self.errorDesc, BorderLayout.CENTER) errorButtonsPanel = JPanel(GridLayout(0, 5, 0, 0)) errorButtonsPanel.add(self.errorInfoBtn) errorButtonsPanel.add(self.notErrorBtn) errorButtonsPanel.add(self.ignoreBtn) errorButtonsPanel.add(self.correctedBtn) errorButtonsPanel.add(self.nextBtn) self.panel2.add(errorButtonsPanel, BorderLayout.PAGE_END) #Layout self.tabbedPane = JTabbedPane() self.tabbedPane.addTab(self.app.strings.getString("Download"), None, panel1, self.app.strings.getString("download_tab")) mainPnl.add(self.tabbedPane, BorderLayout.CENTER) self.createLayout(mainPnl, False, None) def add_data_to_models(self, tool): """Add data of a tool to the models of the dialog components """ #tools combobox model if tool == self.app.favouritesTool: self.toolsComboModel.addElement(JSeparator()) self.toolsComboModel.addElement(tool) #views combobox model tool.viewsComboModel = DefaultComboBoxModel() for view in tool.views: tool.viewsComboModel.addElement(view.title) #checks table, one TableModel for each view, of each tool columns = ["", self.app.strings.getString("Check"), self.app.strings.getString("Errors")] for view in tool.views: tableRows = [] for check in view.checks: if check.icon is not None: icon = check.icon else: icon = "" errorsNumber = "" tableRows.append([icon, check.title, errorsNumber]) view.tableModel = MyTableModel(tableRows, columns) def update_favourite_zone_indicator(self): #icon if self.app.favZone is not None: self.favAreaIndicator.setIcon(self.app.favZone.icon) #tooltip messageArguments = array([self.app.favZone.name], String) formatter = MessageFormat("") formatter.applyPattern(self.app.strings.getString("favAreaIndicator_tooltip")) msg = formatter.format(messageArguments) self.favAreaIndicator.setToolTipText(msg) #status self.favAreaIndicator.setVisible(self.app.favouriteZoneStatus) def set_checksTextFld_color(self, color): """Change color of textField under checksTable """ colors = {"white": (255, 255, 255), "black": (0, 0, 0), "green": (100, 200, 0), "red": (200, 0, 0)} if color == "default": self.statsPanel.background = self.statsPanel_def_color self.checksTextFld.foreground = colors["black"] else: self.statsPanel.background = colors[color] self.checksTextFld.foreground = colors["white"] def change_selection(self, source): """Change comboboxes and checks table selections after a selection has been made by the user """ if source in ("menu", "layer", "add favourite"): self.app.selectionChangedFromMenuOrLayer = True self.toolsCombo.setSelectedItem(self.app.selectedTool) self.viewsCombo.setModel(self.app.selectedTool.viewsComboModel) self.viewsCombo.setSelectedItem(self.app.selectedView.title) self.checksTable.setModel(self.app.selectedTableModel) self.refresh_checksTable_columns_geometries() for i, c in enumerate(self.app.selectedView.checks): if c == self.app.selectedChecks[0]: break self.checksTable.setRowSelectionInterval(i, i) self.app.selectionChangedFromMenuOrLayer = False else: self.app.selectionChangedFromMenuOrLayer = False if source == "toolsCombo": self.viewsCombo.setModel(self.app.selectedTool.viewsComboModel) self.viewsCombo.setSelectedIndex(0) elif source == "viewsCombo": self.checksTable.setModel(self.app.selectedTableModel) self.refresh_checksTable_columns_geometries() if self.app.selectedView.checks != []: # favourite checks may be none self.checksTable.setRowSelectionInterval(0, 0) def refresh_checksTable_columns_geometries(self): self.checksTable.getColumnModel().getColumn(0).setCellRenderer(self.iconrenderer) self.checksTable.getColumnModel().getColumn(0).setMaxWidth(25) self.checksTable.getColumnModel().getColumn(2).setMaxWidth(60) def activate_error_tab(self, status): if status: if self.tabbedPane.getTabCount() == 1: self.tabbedPane.addTab(self.app.strings.getString("Fix"), None, self.panel2, self.app.strings.getString("fix_tab")) else: if self.tabbedPane.getTabCount() == 2: self.tabbedPane.remove(1) def update_checks_buttons(self): """This method sets the status of downloadBtn and startBtn """ #none check selected if len(self.app.selectedChecks) == 0: self.downloadBtn.setEnabled(False) self.startBtn.setEnabled(False) else: #some check selected self.downloadBtn.setEnabled(True) if len(self.app.selectedChecks) > 1: self.startBtn.setEnabled(False) else: #only one check is selected self.app.errors = self.app.selectedChecks[0].errors if self.app.errors is None or len(self.app.errors) == 0: #errors file has not been downloaded and parsed yet self.startBtn.setEnabled(False) else: #errors file has been downloaded and parsed if self.app.selectedChecks[0].toDo == 0: #all errors have been corrected self.startBtn.setEnabled(False) else: self.startBtn.setEnabled(True) #self.nextBtn.setEnabled(True) def update_error_buttons(self, mode): """This method sets the status of: ignoreBtn, falsePositiveBtn, correctedBtn, nextBtn """ if mode == "new error": status = True else: status = False if self.app.selectedChecks[0].tool.fixedFeedbackMode is None: self.correctedBtn.setEnabled(False) else: self.correctedBtn.setEnabled(status) if self.app.selectedChecks[0].tool.falseFeedbackMode is None: self.notErrorBtn.setEnabled(False) else: self.notErrorBtn.setEnabled(status) self.errorInfoBtn.setEnabled(status) self.ignoreBtn.setEnabled(status) if mode in ("reset", "review end"): self.nextBtn.setEnabled(False) elif mode in ("errors downloaded", "show stats", "new error"): self.nextBtn.setEnabled(True) def update_text_fields(self, mode, errorInfo=""): """This method updates the text in: checksTextFld, errorDesc, errorTextFld """ self.errorDesc.text = "" if mode == "review end": cheksTextColor = "green" checksText = self.app.strings.getString("All_errors_reviewed.") errorText = self.app.strings.getString("All_errors_reviewed.") elif mode == "reset": cheksTextColor = "default" checksText = "" errorText = "" elif mode == "show stats": cheksTextColor = "default" checksText = "%s %d / %s" % ( self.app.strings.getString("to_do"), self.app.selectedChecks[0].toDo, len(self.app.selectedChecks[0].errors)) #print "checks text", checksText errorText = "%s%s %d / %s" % ( errorInfo, self.app.strings.getString("to_do"), self.app.selectedChecks[0].toDo, len(self.app.selectedChecks[0].errors)) #print "error text", errorText if self.app.selectedError is not None and self.app.selectedError.desc != "": self.errorDesc.text = "<html>%s</html>" % self.app.selectedError.desc self.set_checksTextFld_color(cheksTextColor) self.checksTextFld.text = checksText self.errorTextFld.text = errorText self.update_statsPanel_status() def update_statsPanel_status(self): if self.checksTextFld.text == "" and not self.app.favouriteZoneStatus: self.statsPanel.setVisible(False) else: self.statsPanel.setVisible(True)
class PreferencesFrame(JFrame, ActionListener, WindowListener, ItemListener, HyperlinkListener): """Dialog with preferences """ def __init__(self, parent, title, app): from javax.swing import JCheckBox, JRadioButton, ButtonGroup self.app = app border = BorderFactory.createEmptyBorder(5, 7, 5, 7) self.getContentPane().setBorder(border) self.getContentPane().setLayout(BorderLayout(0, 5)) self.tabbedPane = JTabbedPane() #1 Tab: general panel1 = JPanel() panel1.setBorder(BorderFactory.createEmptyBorder(7, 7, 7, 7)) panel1.setLayout(BoxLayout(panel1, BoxLayout.PAGE_AXIS)) #Checkbutton to enable/disable update check when script starts self.updateCBtn = JCheckBox(self.app.strings.getString("updateCBtn")) self.updateCBtn.setToolTipText(self.app.strings.getString("updateCBtn_tooltip")) #Download tools downloadBtn = JButton(self.app.strings.getString("updatesBtn"), ImageProvider.get("dialogs", "refresh"), actionPerformed=self.on_downloadBtn_clicked) downloadBtn.setToolTipText(self.app.strings.getString("updatesBtn_tooltip")) #Checkbuttons for enabling/disabling tools toolsPanel = JPanel(BorderLayout(0, 5)) title = self.app.strings.getString("enable_disable_tools") toolsPanel.setBorder(BorderFactory.createTitledBorder(title)) infoLbl = JLabel(self.app.strings.getString("JOSM_restart_warning")) infoLbl.setFont(infoLbl.getFont().deriveFont(Font.ITALIC)) toolsPanel.add(infoLbl, BorderLayout.PAGE_START) toolsStatusPane = JPanel(GridLayout(len(self.app.realTools), 0)) self.toolsCBtns = [] for tool in self.app.realTools: toolCBtn = JCheckBox() toolCBtn.addItemListener(self) toolLbl = JLabel(tool.title, tool.bigIcon, JLabel.LEFT) self.toolsCBtns.append(toolCBtn) toolPane = JPanel() toolPane.setLayout(BoxLayout(toolPane, BoxLayout.X_AXIS)) toolPane.add(toolCBtn) toolPane.add(toolLbl) toolsStatusPane.add(toolPane) toolsPanel.add(toolsStatusPane, BorderLayout.CENTER) #Radiobuttons for enabling/disabling layers when a new one #is added layersPanel = JPanel(GridLayout(0, 1)) title = self.app.strings.getString("errors_layers_manager") layersPanel.setBorder(BorderFactory.createTitledBorder(title)) errorLayersLbl = JLabel(self.app.strings.getString("errors_layers_info")) errorLayersLbl.setFont(errorLayersLbl.getFont().deriveFont(Font.ITALIC)) layersPanel.add(errorLayersLbl) self.layersRBtns = {} group = ButtonGroup() for mode in self.app.layersModes: layerRBtn = JRadioButton(self.app.strings.getString("%s" % mode)) group.add(layerRBtn) layersPanel.add(layerRBtn) self.layersRBtns[mode] = layerRBtn #Max number of errors text field self.maxErrorsNumberTextField = JTextField() self.maxErrorsNumberTextField.setToolTipText(self.app.strings.getString("maxErrorsNumberTextField_tooltip")) self.maxErrorsNumberTFieldDefaultBorder = self.maxErrorsNumberTextField.getBorder() self.maxErrorsNumberTextField.getDocument().addDocumentListener(ErrNumTextListener(self)) #layout self.updateCBtn.setAlignmentX(Component.LEFT_ALIGNMENT) panel1.add(self.updateCBtn) panel1.add(Box.createRigidArea(Dimension(0, 15))) downloadBtn.setAlignmentX(Component.LEFT_ALIGNMENT) panel1.add(downloadBtn) panel1.add(Box.createRigidArea(Dimension(0, 15))) toolsPanel.setAlignmentX(Component.LEFT_ALIGNMENT) panel1.add(toolsPanel) panel1.add(Box.createRigidArea(Dimension(0, 15))) layersPanel.setAlignmentX(Component.LEFT_ALIGNMENT) panel1.add(layersPanel) panel1.add(Box.createRigidArea(Dimension(0, 15))) maxErrP = JPanel(BorderLayout(5, 0)) maxErrP.add(JLabel(self.app.strings.getString("max_errors_number")), BorderLayout.LINE_START) maxErrP.add(self.maxErrorsNumberTextField, BorderLayout.CENTER) p = JPanel(BorderLayout()) p.add(maxErrP, BorderLayout.PAGE_START) p.setAlignmentX(Component.LEFT_ALIGNMENT) panel1.add(p) self.tabbedPane.addTab(self.app.strings.getString("tab_1_title"), None, panel1, None) #2 Tab: favourite zones panel2 = JPanel(BorderLayout(5, 15)) panel2.setBorder(BorderFactory.createEmptyBorder(7, 7, 7, 7)) #status topPanel = JPanel() topPanel.setLayout(BoxLayout(topPanel, BoxLayout.Y_AXIS)) infoPanel = HtmlPanel(self.app.strings.getString("fav_zones_info")) infoPanel.getEditorPane().addHyperlinkListener(self) infoPanel.setAlignmentX(Component.LEFT_ALIGNMENT) self.favZoneStatusCBtn = JCheckBox(self.app.strings.getString("activate_fav_area"), actionListener=self) self.favZoneStatusCBtn.setToolTipText(self.app.strings.getString("activate_fav_area_tooltip")) self.favZoneStatusCBtn.setAlignmentX(Component.LEFT_ALIGNMENT) topPanel.add(infoPanel) topPanel.add(Box.createRigidArea(Dimension(0, 10))) topPanel.add(self.favZoneStatusCBtn) #table self.zonesTable = JTable() tableSelectionModel = self.zonesTable.getSelectionModel() tableSelectionModel.addListSelectionListener(ZonesTableListener(self)) columns = ["", self.app.strings.getString("Type"), self.app.strings.getString("Name")] tableModel = ZonesTableModel([], columns) self.zonesTable.setModel(tableModel) self.scrollPane = JScrollPane(self.zonesTable) #map self.zonesMap = JMapViewer() self.zonesMap.setZoomContolsVisible(False) self.zonesMap.setMinimumSize(Dimension(100, 200)) #buttons self.removeBtn = JButton(self.app.strings.getString("Remove"), ImageProvider.get("dialogs", "delete"), actionPerformed=self.on_removeBtn_clicked) self.removeBtn.setToolTipText(self.app.strings.getString("remove_tooltip")) newBtn = JButton(self.app.strings.getString("New"), ImageProvider.get("dialogs", "add"), actionPerformed=self.on_newBtn_clicked) newBtn.setToolTipText(self.app.strings.getString("new_tooltip")) #layout panel2.add(topPanel, BorderLayout.PAGE_START) panel2.add(self.scrollPane, BorderLayout.LINE_START) panel2.add(self.zonesMap, BorderLayout.CENTER) self.buttonsPanel = JPanel() self.buttonsPanel.add(self.removeBtn) self.buttonsPanel.add(newBtn) panel2.add(self.buttonsPanel, BorderLayout.PAGE_END) self.tabbedPane.addTab(self.app.strings.getString("tab_2_title"), None, panel2, None) #3 Tab Tools options panel3 = JPanel() panel3.setLayout(BoxLayout(panel3, BoxLayout.Y_AXIS)) panel3.setBorder(BorderFactory.createEmptyBorder(7, 7, 7, 7)) for tool in self.app.realTools: if hasattr(tool, 'prefs'): p = JPanel(FlowLayout(FlowLayout.LEFT)) p.setBorder(BorderFactory.createTitledBorder(tool.title)) p.add(tool.prefsGui) panel3.add(p) self.tabbedPane.addTab(self.app.strings.getString("tab_3_title"), None, panel3, None) self.add(self.tabbedPane, BorderLayout.CENTER) exitPanel = JPanel() saveBtn = JButton(self.app.strings.getString("OK"), ImageProvider.get("ok"), actionPerformed=self.on_saveBtn_clicked) cancelBtn = JButton(self.app.strings.getString("cancel"), ImageProvider.get("cancel"), actionPerformed=self.on_cancelBtn_clicked) saveBtn.setToolTipText(self.app.strings.getString("save_preferences")) saveBtn.setAlignmentX(0.5) exitPanel.add(saveBtn) exitPanel.add(cancelBtn) self.add(exitPanel, BorderLayout.PAGE_END) self.addWindowListener(self) self.pack() def windowClosing(self, windowEvent): self.on_cancelBtn_clicked() def hyperlinkUpdate(self, e): if e.getEventType() == HyperlinkEvent.EventType.ACTIVATED: OpenBrowser.displayUrl(e.getURL().toString()) def itemStateChanged(self, e): """A ttol has been activated/deactivated. Check if at least one tool is on. """ if all(not button.isSelected() for button in self.toolsCBtns): JOptionPane.showMessageDialog( Main.parent, self.app.strings.getString("tools_disabled_warning"), self.app.strings.getString("tools_disabled_warning_title"), JOptionPane.WARNING_MESSAGE) source = e.getItemSelectable() source.setSelected(True) def actionPerformed(self, e=None): """Enable/disable favourite zones panel """ for container in (self.scrollPane, self.buttonsPanel): self.enableComponents(container, self.favZoneStatusCBtn.isSelected()) if self.favZoneStatusCBtn.isSelected(): self.check_removeBtn_status() def enableComponents(self, container, enable): components = container.getComponents() for component in components: component.setEnabled(enable) if isinstance(component, Container): self.enableComponents(component, enable) def on_downloadBtn_clicked(self, e): update_checker.Updater(self.app, "manual") def clean_map(self): """Remove all rectangles and polygons from the map """ self.zonesMap.removeAllMapRectangles() self.zonesMap.removeAllMapPolygons() def update_gui_from_preferences(self): """Update gui status of preferences frame from config file """ #print "\n- updating Preferences gui" onOff = {"on": True, "off": False} #1 Tab #check for update self.updateCBtn.setSelected(onOff[self.app.checkUpdate]) #tools status, enabled or not for toolIndex, tool in enumerate(self.app.realTools): if "tool.%s" % tool.name in self.app.properties.keys(): configstatus = self.app.properties.getProperty("tool.%s" % tool.name) else: configstatus = "on" # new tool self.toolsCBtns[toolIndex].setSelected(onOff[configstatus]) #layers preferences for mode, button in self.layersRBtns.iteritems(): button.setSelected(mode == self.app.layersMode) #max errors number self.maxErrorsNumberTextField.setText(str(self.app.maxErrorsNumber)) #stats panel self.app.dlg.update_favourite_zone_indicator() #2 Tab #favourite area self.update_favourite_area_gui_from_preferences() self.app.dlg.update_statsPanel_status() #3 Tab #tools preferences for tool in self.app.allTools: if hasattr(tool, 'prefs') and tool.prefsGui is not None: tool.prefsGui.update_gui(tool.prefs) def update_favourite_area_gui_from_preferences(self): #status self.favZoneStatusCBtn.setSelected(self.app.favouriteZoneStatus) #table #store zones to a temporary list, used to store changes #and save them when preferences dialog is closed self.app.tempZones = list(self.app.zones) self.zonesTable.getModel().setNumRows(0) for zone in self.app.tempZones: self.zonesTable.getModel().addRow([zone.country, zone.icon, zone.name]) if self.app.favZone is not None: selectedRow = self.app.tempZones.index(self.app.favZone) self.zonesTable.setRowSelectionInterval(selectedRow, selectedRow) self.zonesTable.getColumnModel().getColumn(0).setMaxWidth(30) self.zonesTable.getColumnModel().getColumn(1).setMaxWidth(50) #enable or disable favourite zone buttons self.actionPerformed() ### fav area editing buttons ########################################### def on_removeBtn_clicked(self, e): rowsNum = self.zonesTable.getSelectedRows() rowsNum.reverse() for rowNum in rowsNum: del self.app.tempZones[rowNum] self.zonesTable.getModel().removeRow(rowNum) if len(self.app.tempZones) != 0: if rowNum == 0: self.zonesTable.setRowSelectionInterval(0, 0) else: self.zonesTable.setRowSelectionInterval(rowNum - 1, rowNum - 1) self.check_removeBtn_status() def check_removeBtn_status(self): if self.app.tempZones != [] and len(self.zonesTable.getSelectedRows()) != 0: self.removeBtn.setEnabled(True) else: self.removeBtn.setEnabled(False) self.clean_map() def on_newBtn_clicked(self, e): try: self.newZoneDialog except AttributeError: self.newZoneDialog = NewZoneDialog(self.app) bbox = self.app.get_frame_bounds() self.app.newZone = Zone(self.app, self.app.strings.getString("New_zone"), "rectangle", ",".join(["%0.4f" % x for x in bbox]), "") self.newZoneDialog.update_gui_from_preferences() self.newZoneDialog.show() ### Exit from preferences ############################################## def on_cancelBtn_clicked(self, event=None): if hasattr(self, "newZoneDialog") and self.newZoneDialog.isVisible(): self.newZoneDialog.close_dialog() self.dispose() def on_saveBtn_clicked(self, event): """Read preferences from gui and save them to config.properties file """ #print "\n- saving preferences to config file" onOff = {True: "on", False: "off"} #1 Tab #check for update self.app.properties.setProperty("check_for_update", onOff[self.updateCBtn.isSelected()]) #tools status for toolIndex, tool in enumerate(self.app.realTools): prop = "tool.%s" % tool.name toolCBtn = self.toolsCBtns[toolIndex] self.app.properties.setProperty(prop, onOff[toolCBtn.isSelected()]) #layers preferences for mode, button in self.layersRBtns.iteritems(): if button.isSelected(): self.app.properties.setProperty("layers_mode", mode) break #max errors number try: num = Integer.parseInt(self.maxErrorsNumberTextField.getText()) except NumberFormatException: num = "" self.app.properties.setProperty("max_errors_number", str(num)) #2 Tab #Favourite zones changes = {"new": [z for z in self.app.tempZones if not z in self.app.zones], "deleted": [z for z in self.app.zones if not z in self.app.tempZones]} #delete files of removed favourite zones for zone in changes["deleted"]: f = File(File.separator.join([self.app.SCRIPTDIR, "configuration", "favourite_zones", "%s.txt" % zone.name])) f.delete() #create files for new favourite zones for zone in changes["new"]: print "\nsave new zone", zone.name fileName = File.separator.join([self.app.SCRIPTDIR, "configuration", "favourite_zones", "%s.txt" % zone.name]) f = open(fileName, "w") zoneData = zone.geomString if zone.country != "": zoneData += "|" + zone.country f.write(zoneData.encode("utf-8")) f.close() self.app.zones = self.app.tempZones if len(self.app.zones) == 0: self.app.favZone = None self.app.properties.setProperty("favourite_area.name", "") self.favZoneStatusCBtn.setSelected(False) else: if len(self.zonesTable.getSelectedRows()) == 0: self.app.favZone = self.app.zones[0] else: self.app.favZone = self.app.zones[self.zonesTable.getSelectedRows()[0]] self.app.properties.setProperty("favourite_area.name", self.app.favZone.name) favZoneStatus = self.favZoneStatusCBtn.isSelected() self.app.properties.setProperty("favourite_area.status", onOff[favZoneStatus]) self.app.favouriteZoneStatus = favZoneStatus #stats panel self.app.dlg.update_favourite_zone_indicator() self.app.dlg.update_statsPanel_status() #3 Tab #tools preferences for tool in self.app.allTools: if hasattr(tool, 'prefs') and tool.prefsGui is not None: for pref, value in tool.prefsGui.read_gui().iteritems(): prefKey = "tool.%s.%s" % (tool.name, pref) self.app.properties.setProperty(prefKey, value) self.app.save_config() self.dispose()
class BurpExtender(IBurpExtender, IBurpExtenderCallbacks, IIntruderPayloadProcessor, ITab, IExtensionStateListener): def registerExtenderCallbacks( self, callbacks): self._helpers = callbacks.getHelpers() callbacks.setExtensionName("JWT FuzzHelper") callbacks.registerIntruderPayloadProcessor(self) callbacks.registerExtensionStateListener(self) self._stdout = PrintWriter(callbacks.getStdout(), True) self._stderr = PrintWriter(callbacks.getStderr(), True) # Holds values passed by user from Configuration panel self._fuzzoptions = { "target" : "Header", "selector" : None, "signature" : False, "algorithm" : "HS256", "key" : "", "key_cmd" : "" } self._isNone = lambda val: isinstance(val, type(None)) # Configuration panel Layout self._configurationPanel = JPanel() gridBagLayout = GridBagLayout() gridBagLayout.columnWidths = [ 0, 0, 0] gridBagLayout.rowHeights = [ 10, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ] gridBagLayout.columnWeights = [ 0.0, 0.0, 0.0 ] gridBagLayout.rowWeights = [0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 1.0] self._configurationPanel.setLayout(gridBagLayout) # Setup tabs self._tabs = JTabbedPane() self._tabs.addTab('Configuration',self._configurationPanel) #self._tabs.addTab('Help',self._helpPanel) # Target Options targetLabel = JLabel("Target Selection (Required): ") targetLabel.setFont(Font("Tahoma",Font.BOLD, 12)) c = GridBagConstraints() c.gridx = 0 c.gridy = 1 c.insets = Insets(0,10,0,0) c.anchor = GridBagConstraints.LINE_END self._configurationPanel.add(targetLabel,c) options = [ 'Header', 'Payload' ] self._targetComboBox = JComboBox(options) c = GridBagConstraints() c.gridx = 1 c.gridy = 1 c.anchor = GridBagConstraints.LINE_START self._configurationPanel.add(self._targetComboBox,c) # Help Button self._helpButton = JButton("Help", actionPerformed=self.helpMenu) c = GridBagConstraints() c.gridx = 2 c.gridy = 1 c.anchor = GridBagConstraints.FIRST_LINE_START self._configurationPanel.add(self._helpButton,c) # Selector Options self._selectorLabel = JLabel("JSON Selector [Object Identifier-Index Syntax] (Required): ") self._selectorLabel.setFont(Font("Tahoma",Font.BOLD, 12)) c = GridBagConstraints() c.gridx = 0 c.gridy = 2 c.insets = Insets(0,10,0,0) c.anchor = GridBagConstraints.LINE_END self._configurationPanel.add(self._selectorLabel, c) self._selectorTextField = JTextField('',50) c = GridBagConstraints() c.gridx = 1 c.gridy = 2 self._configurationPanel.add(self._selectorTextField, c) # Regex option self._regexLabel = JLabel("Use regex as JSON Selector? (Optional): ") self._regexLabel.setFont(Font("Tahoma",Font.BOLD, 12)) c = GridBagConstraints() c.gridx = 0 c.gridy = 3 c.insets = Insets(0,0,0,0) c.anchor = GridBagConstraints.LINE_END self._configurationPanel.add(self._regexLabel,c) self._regexCheckBox = JCheckBox("", actionPerformed=self.regexSelector) c = GridBagConstraints() c.gridx = 1 c.gridy = 3 c.anchor = GridBagConstraints.FIRST_LINE_START self._configurationPanel.add(self._regexCheckBox,c) # Signature Options generateSignatureLabel = JLabel("Generate signature? (Required): ") generateSignatureLabel.setFont(Font("Tahoma",Font.BOLD, 12)) c = GridBagConstraints() c.gridx = 0 c.gridy = 4 c.insets = Insets(0,10,0,0) c.anchor = GridBagConstraints.LINE_END self._configurationPanel.add(generateSignatureLabel,c) options = ["False", "True"] self._generateSignatureComboBox = JComboBox(options) c = GridBagConstraints() c.gridx = 1 c.gridy = 4 c.anchor = GridBagConstraints.LINE_START self._configurationPanel.add(self._generateSignatureComboBox,c) signatureAlgorithmLabel = JLabel("Signature Algorithm (Optional): ") signatureAlgorithmLabel.setFont(Font("Tahoma",Font.BOLD, 12)) c = GridBagConstraints() c.gridx = 0 c.gridy = 5 c.insets = Insets(0,10,0,0) c.anchor = GridBagConstraints.LINE_END self._configurationPanel.add(signatureAlgorithmLabel,c) options = ["None", "HS256","HS384","HS512","ES256","ES384","ES512","RS256","RS384","RS512","PS256","PS256","PS384","PS512"] self._algorithmSelectionComboBox = JComboBox(options) c = GridBagConstraints() c.gridx = 1 c.gridy = 5 c.anchor = GridBagConstraints.LINE_START self._configurationPanel.add(self._algorithmSelectionComboBox,c) # Signing key options self._signingKeyLabel = JLabel("Signing Key (Optional): ") self._signingKeyLabel.setFont(Font("Tahoma",Font.BOLD, 12)) c = GridBagConstraints() c.gridx = 0 c.gridy = 6 c.insets = Insets(0,10,0,0) c.anchor = GridBagConstraints.LINE_END self._configurationPanel.add(self._signingKeyLabel,c) self.addSigningKeyTextArea() self._fromFileTextField = JTextField('',50) fromFileLabel = JLabel("Signing key from file? (Optional): ") fromFileLabel.setFont(Font("Tahoma",Font.BOLD, 12)) c = GridBagConstraints() c.gridx = 0 c.gridy = 7 c.insets = Insets(0,0,0,0) c.anchor = GridBagConstraints.LINE_END self._configurationPanel.add(fromFileLabel,c) self._fromFileCheckBox = JCheckBox("", actionPerformed=self.fromFile) c = GridBagConstraints() c.gridx = 1 c.gridy = 7 c.anchor = GridBagConstraints.FIRST_LINE_START self._configurationPanel.add(self._fromFileCheckBox,c) self._fromCmdTextField = JTextField('',50) fromCmdLabel = JLabel("Signing key from command? (Optional): ") fromCmdLabel.setFont(Font("Tahoma",Font.BOLD, 12)) c = GridBagConstraints() c.gridx = 0 c.gridy = 8 c.insets = Insets(0,0,0,0) c.anchor = GridBagConstraints.LINE_END self._configurationPanel.add(fromCmdLabel,c) self._fromCmdCheckBox = JCheckBox("", actionPerformed=self.fromCmd) c = GridBagConstraints() c.gridx = 1 c.gridy = 8 c.anchor = GridBagConstraints.FIRST_LINE_START self._configurationPanel.add(self._fromCmdCheckBox,c) self._saveButton = JButton("Save Configuration", actionPerformed=self.saveOptions) self._saveButton.setText("Save Configuration") c = GridBagConstraints() c.gridx = 1 c.gridy = 9 c.anchor = GridBagConstraints.FIRST_LINE_START self._configurationPanel.add(self._saveButton,c) callbacks.customizeUiComponent(self._configurationPanel) callbacks.customizeUiComponent(self._tabs) callbacks.addSuiteTab(self) self._stdout.println("[JWT FuzzHelper] Loaded successfully") return def getProcessorName(self): return "JWT Fuzzer" def extensionUnloaded(self): del self._configurationPanel return # Intruder logic function def processPayload(self, currentPayload, originalPayload, baseValue): dataParameter = self._helpers.bytesToString( self._helpers.urlDecode(baseValue) ) # utf-8 encode header,payload,signature = [unicode(s).encode('utf-8') for s in dataParameter.split(".",3)] decoded_header = self._helpers.bytesToString( self._helpers.base64Decode(header + "=" * (-len(header) % 4)) ) decoded_payload = self._helpers.bytesToString( self._helpers.base64Decode(payload+"=" * (-len(payload) % 4)) ) # Decode header and payload, preserving order if they are JSON objects # Decode header try: header_dict = json.loads(decoded_header, object_pairs_hook=OrderedDict) except ValueError: raise RuntimeException("[JWT FuzzHelper] Error: ValueError. Failed to decode header!") except Exception as e: self._stderr.println("[ERROR] Encountered an unknown error when decoding header:\n{}\nCarrying on...".format(e)) # Decode payload # Payload does not have to be a JSON object. # Ref: https://github.com/auth0/node-jsonwebtoken#usage payload_is_string = False try: payload_dict = json.loads(decoded_payload, object_pairs_hook=OrderedDict) except ValueError: payload_is_string = True payload_dict = decoded_payload except Exception as e: self._stderr.println("[ERROR] Encountered an unknown error when decoding payload:\n{}\nCarrying on...".format(e)) target = header_dict if self._fuzzoptions["target"] == "Header" else payload_dict selector = self._fuzzoptions["selector"] # If using Object Identifier-Index then retrieve the # value specified by the selector, # if this value does not exist, assume the user # wants to add the value that would have been specified # by the selector to the desired JWT segment (this behavior will # be noted in the help docs) intruderPayload = self._helpers.bytesToString(currentPayload) if not self._fuzzoptions["regex"]: if selector != [""]: try: value = self.getValue(target, selector) except Exception: target = self.buildDict(target, selector) if not self._isNone(selector) and selector != [""]: target = self.setValue(target, selector, intruderPayload) # Simple match-replace for regex if self._fuzzoptions["regex"]: target_string = target if payload_is_string else json.dumps(target) target_string = re.sub(selector, intruderPayload, target_string) target = target_string if payload_is_string else json.loads(target_string, object_pairs_hook=OrderedDict) if self._fuzzoptions["target"] == "Payload": payload_dict = target else: header_dict = target algorithm = self._fuzzoptions["algorithm"] if self._fuzzoptions["signature"]: # pyjwt requires lowercase 'none'. If user wants to try # "none", "NonE", "nOnE", etc... they should use .alg # as selector, delete sig from intruder and use those # permutations as their fuzz list (outlined in help docs) # and keep "Generate Signature" as False algorithm = "none" if algorithm.lower() == "none" else algorithm header_dict["alg"] = algorithm header = json.dumps(header_dict, separators=(",",":")) payload = payload_dict if payload_is_string else json.dumps(payload_dict, separators=(",",":")) header = self._helpers.base64Encode(header).strip("=") payload = self._helpers.base64Encode(payload).strip("=") contents = header + "." + payload key = self._fuzzoptions["key"] if len(self._fuzzoptions["key_cmd"]) > 0: # we provide 'contents' value as an only argument to key-generating command # it is expected that the command will print only the signature signature = check_output([self._fuzzoptions["key_cmd"], contents]) modified_jwt = contents + "." + signature elif self._fuzzoptions["signature"]: # pyjwt throws error when using a public key in symmetric alg (for good reason of course), # must do natively to support algorithmic sub attacks if algorithm.startswith("HS"): if algorithm == "HS256": hmac_algorithm = hashlib.sha256 elif algorithm == "HS384": hmac_algorithm = hashlib.sha384 else: hmac_algorithm = hashlib.sha512 signature = self._helpers.base64Encode( hmac.new( key, contents, hmac_algorithm ).digest() ).strip("=") modified_jwt = contents + "." +signature # JWT can't sign non-JSON payloads. WTF. This block is for non-JSON payloads. elif algorithm.startswith("RS") and payload_is_string: if algorithm == "RS256": rsa_algorithm = "SHA-256" elif algorithm == "RS384": rsa_algorithm = "SHA-384" else: rsa_algorithm = "SHA-512" privkey = rsa.PrivateKey.load_pkcs1(key) signature = rsa.sign(contents,privkey,rsa_algorithm) signature = base64.b64encode(signature).encode('utf-8').replace("=", "") modified_jwt = contents + "." + signature else: # Use pyjwt when using asymmetric alg if algorithm == "none": key = "" modified_jwt = jwt.encode(payload_dict,key,algorithm=algorithm,headers=header_dict) else: modified_jwt = contents + "." + signature return self._helpers.stringToBytes(modified_jwt) #----------------------- # getValue: # @return: A value at arbitrary depth in dictionary # @throws: TypeError #----------------------- def getValue(self, dictionary, values): return reduce(dict.__getitem__, values, dictionary) #----------------------- # buildDict: # @note: Will build dictionary of arbitrary depth #----------------------- def buildDict(self, dictionary, keys): if self._isNone(keys): return dictionary root = current = dictionary for key in keys: if key not in current: current[key] = {} current = current[key] return root #---------------------- # setValue: # @note: Will set key of arbitrary depth #----------------------- def setValue(self, dictionary, keys, value): root = current = dictionary for i,key in enumerate(keys): if i == len(keys) - 1: current[key] = value break if key in current: current = current[key] else: # Should never happen current = self.buildDict(current, keys) return root #----------------------- # addSigningKeyTextArea: # @note: Will toggle if fromFile selected. Be DRY. #---------------------- def addSigningKeyTextArea(self): self._signingKeyTextArea = JTextArea() self._signingKeyTextArea.setColumns(50) self._signingKeyTextArea.setRows(10) self._signingKeyScrollPane = JScrollPane(self._signingKeyTextArea) c = GridBagConstraints() c.gridx = 1 c.gridy = 6 c.anchor = GridBagConstraints.LINE_START self._configurationPanel.add(self._signingKeyScrollPane,c) def addSigningKeyFromFileTextField(self): c = GridBagConstraints() c.gridx = 1 c.gridy = 6 self._configurationPanel.add(self._fromFileTextField, c) def addSigningKeyFromCmdTextField(self): c = GridBagConstraints() c.gridx = 1 c.gridy = 6 self._configurationPanel.add(self._fromCmdTextField, c) #----------------------- # End Helpers #----------------------- #----------------------- # Implement ITab #----------------------- def getTabCaption(self): return "JWT FuzzHelper" def getUiComponent(self): return self._tabs #--------------------------- # Save configuration options #--------------------------- def saveOptions(self,event): self._fuzzoptions["target"] = self._targetComboBox.getSelectedItem() self._fuzzoptions["selector"] = self._selectorTextField.getText() self._fuzzoptions["signature"] = True if self._generateSignatureComboBox.getSelectedItem() == "True" else False self._fuzzoptions["algorithm"] = self._algorithmSelectionComboBox.getSelectedItem() self._fuzzoptions["key_cmd"] = "" if self._fromFileCheckBox.isSelected(): filename = self._fromFileTextField.getText() if os.path.isdir(filename): self._stderr.println("{} is a directory".format(filename)) return if os.path.exists(filename): with open(filename, 'rb') as f: self._fuzzoptions["key"] = f.read() elif self._fromCmdCheckBox.isSelected(): self._fuzzoptions["key_cmd"] = self._fromCmdTextField.getText() else: self._fuzzoptions["key"] = unicode(self._signingKeyTextArea.getText()).encode("utf-8") # RSA keys need to end with a line break. Many headaches because of this. if not self._fuzzoptions["key"].endswith("\n") and self._fuzzoptions["algorithm"].startswith("RS"): self._fuzzoptions["key"] += "\n" self._stdout.println("[JWT FuzzHelper] Saved options:\n{}".format(self._fuzzoptions)) # Sanity check selector if it's not a regular expression self._fuzzoptions["regex"] = self._regexCheckBox.isSelected() if not self._regexCheckBox.isSelected(): m = re.search("(\.\w+)+",self._fuzzoptions["selector"]) if self._fuzzoptions["selector"] != "." and (isinstance(m,type(None)) or m.group(0) != self._fuzzoptions["selector"]): self._saveButton.setText("Invalid JSON Selector!") else: self._fuzzoptions["selector"] = self._fuzzoptions["selector"].split(".")[1:] self._saveButton.setText("Saved!") # Sanity check the regular expression else: try: re.compile(self._fuzzoptions["selector"]) self._saveButton.setText("Saved!") except re.error: self._saveButton.setText("Invalid Regex!") return #------------------------- # From file options #------------------------ def fromFile(self,event): if self._fromFileCheckBox.isSelected(): self._signingKeyLabel.setText("Path to Signing Key (Optional): ") self._configurationPanel.remove(self._signingKeyScrollPane) self.addSigningKeyFromFileTextField() else: self._signingKeyLabel.setText("Signing Key (Optional): ") self._configurationPanel.remove(self._fromFileTextField) self.addSigningKeyTextArea() self._configurationPanel.repaint() return def fromCmd(self,event): if self._fromCmdCheckBox.isSelected(): self._signingKeyLabel.setText("Path to Signing Cmd (Optional): ") self._configurationPanel.remove(self._signingKeyScrollPane) self.addSigningKeyFromCmdTextField() else: self._signingKeyLabel.setText("Signing Key (Optional): ") self._configurationPanel.remove(self._fromCmdTextField) self.addSigningKeyTextArea() self._configurationPanel.repaint() return def regexSelector(self,event): if self._regexCheckBox.isSelected(): self._selectorLabel.setText("Selector [Regex] (Required): ") else: self._selectorLabel.setText("JSON Selector [Object Identifier-Index Syntax] (Required): ") self._configurationPanel.repaint() return #------------------------- # Help popup #------------------------- def helpMenu(self,event): self._helpPopup = JFrame('JWT Fuzzer', size=(550, 450) ); self._helpPopup.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE) helpPanel = JPanel() helpPanel.setPreferredSize(Dimension(550, 450)) helpPanel.setBorder(EmptyBorder(10, 10, 10, 10)) helpPanel.setLayout(BoxLayout(helpPanel, BoxLayout.Y_AXIS)) self._helpPopup.setContentPane(helpPanel) helpHeadingText = JLabel("<html><h2>JWT Fuzzer</h2></html>") authorText = JLabel("<html><p>@author: <pinnace></p></html>") aboutText = JLabel("<html><br /> <p>This extension adds an Intruder payload processor for JWTs.</p><br /></html>") repositoryText = JLabel("<html>Documentation and source code:</html>") repositoryLink = JLabel("<html>- <a href=\"https://github.com/pinnace/burp-jwt-fuzzhelper-extension\">https://github.com/pinnace/burp-jwt-fuzzhelper-extension</a></html>") licenseText = JLabel("<html><br/><p>JWT Fuzzer uses a GPL 3 license. This license does not apply to the dependency below:<p></html>") dependencyLink = JLabel("<html>- <a href=\"https://github.com/jpadilla/pyjwt/blob/master/LICENSE\">pyjwt</a></html>") dependencyLink.addMouseListener(ClickListener()) dependencyLink.setCursor(Cursor.getPredefinedCursor(Cursor.HAND_CURSOR)) repositoryLink.addMouseListener(ClickListener()) repositoryLink.setCursor(Cursor.getPredefinedCursor(Cursor.HAND_CURSOR)) helpPanel.add(helpHeadingText) helpPanel.add(authorText) helpPanel.add(aboutText) helpPanel.add(repositoryText) helpPanel.add(repositoryLink) helpPanel.add(licenseText) helpPanel.add(dependencyLink) self._helpPopup.setSize(Dimension(550, 450)) self._helpPopup.pack() self._helpPopup.setLocationRelativeTo(None) self._helpPopup.setVisible(True) return
def __init__(self): frame = JFrame("S1riu5 Spy") frame.setSize(700, 690) frame.setLocationRelativeTo(None); frame.setLayout(BorderLayout()) tabPane = JTabbedPane(JTabbedPane.TOP) #第一个Tab用来做C段查询 eachIp = self.getIp(HOSTDOMAIN) iList = eachIp.split(".") theIP = iList[0] + "." + iList[1] + "." + iList[2] + ".1/24" panel1 = JPanel() label = JLabel("IP CIDR:") self.textfield1 = JTextField(theIP, 15) button = JButton("SCAN", actionPerformed = self.cNmapScan) self.textArea = JTextArea(40, 65) self.textArea.append("IP: " + eachIp) self.textArea.setLineWrap(True) #激活自动换行功能 self.textArea.setWrapStyleWord(True); # 激活断行不断字功能 panel1.add(label) panel1.add(self.textfield1) panel1.add(button) panel1.add(JScrollPane(self.textArea)) #设置自动滚动条 tabPane.addTab("C segment query ", panel1) #第二个Tab用来做子域名查询 theName = self.getDomain1(HOSTDOMAIN) self.textArea2 = JTextArea(40, 65) #self.textArea.append("IP: " + eachIp) self.textArea2.setLineWrap(True) #激活自动换行功能 self.textArea2.setWrapStyleWord(True) # 激活断行不断字功能 label2 = JLabel("Domain: ") self.textfield2 = JTextField(theName, 15) button2 = JButton("SCAN", actionPerformed = self.subDomain) self.panel2 = JPanel() self.panel2.add(label2) self.panel2.add(self.textfield2) self.panel2.add(button2) #self.panel2.add(scrollPane) self.panel2.add(JScrollPane(self.textArea2)) tabPane.addTab("subDomains", self.panel2) #第三个Tab用来做敏感文件扫描 self.tableData0 = [["1", "2"]] colNames2 = ('url','http code') dataModel3 = DefaultTableModel(self.tableData0, colNames2) self.table3 = JTable(dataModel3) ## label3 = JLabel("URL: ") self.textfield3 = JTextField(HOSTDOMAIN, 15) self.textArea3 = JTextArea(40, 65) #self.textArea.append("IP: " + eachIp) self.textArea3.setLineWrap(True) #激活自动换行功能 self.textArea3.setWrapStyleWord(True) # 激活断行不断字功能 a = 0 b = 0 self.label4 = JLabel(str(a) + "/" + str(b)) # self.chkbox1 = JCheckBox('ASP') self.chkbox2 = JCheckBox('ASPX') self.chkbox3 = JCheckBox('JSP') self.chkbox4 = JCheckBox('PHP') self.chkbox5 = JCheckBox('MDB') self.chkbox6 = JCheckBox('DIR') button3 = JButton("SCAN", actionPerformed = self.senFileScan) panel3 = JPanel() panel3.add(label3) panel3.add(self.textfield3) panel3.add(self.chkbox1) panel3.add(self.chkbox2) panel3.add(self.chkbox3) panel3.add(self.chkbox4) panel3.add(self.chkbox5) panel3.add(self.chkbox6) panel3.add(button3) panel3.add(self.label4) panel3.add(JScrollPane(self.textArea3)) # tabPane.addTab("Sebsitive File", panel3) # frame.add(tabPane) frame.setVisible(True)