Example #1
0
def main():
    print("Scanner App Started...")

    # UI Updating Method
    def update_left_header_label(value):
        """UI Updating Method
        :param value: value to be set in left header
        """
        if value is None:
            # if the provided value is none, then update to the default header
            host_count = DataShare.get_hosts_total()
            host_count_text = f"({host_count}) Hosts Scanned".format()
            left_frame_header_label_var.set(host_count_text)
        else:
            # else
            left_frame_header_label_var.set(value)

    def update_left_header_label_random_waiting_msg():
        """Update waiting header randomly"""
        random_waiting_responses = [
            "This may take a while...", "I'm sorry this will be a while...",
            "Scanning...", "Scanning in Process..."
        ]
        update_left_header_label(random.choice(random_waiting_responses))

    def reset_left_header_label():
        """Update left header with number of hosts scanned"""
        host_count = DataShare.get_hosts_total()
        host_count_text = f"({host_count}) Hosts Scanned".format()
        left_frame_header_label_var.set(host_count_text)

    def reload_hosts_tableview():
        """Update hosts box with scanned hosts"""
        # hosts_listbox.delete(0, tk.END)
        sorted_scanned_hosts = None

        # Sort according to the Host Sort Setting
        reverse_sort = False

        if System.Settings.get_host_sort_type() == System.SortType.alphaDESC:
            reverse_sort = True

        if DataShare.get_hosts():
            sorted_scanned_hosts = sorted(DataShare.get_hosts(),
                                          key=lambda x: (x.get_display_name()),
                                          reverse=reverse_sort)

        if sorted_scanned_hosts is None:
            return

        # Update hosts to the sorted version to ensure details on select are correct
        DataShare.set_hosts(sorted_scanned_hosts)
        reset_left_header_label()

        data = list(
            map(
                lambda host:
                (host.get_ip(), host.get_display_name(), host.get_vendor()),
                sorted_scanned_hosts))

        # We need to reverse the data shown here because the table view will display the data in the reversed order
        # this is needed so that clicking the tableview will result in the correct host being selected: Task189
        hosts_table_view.reload_data(data[::-1])

    def scan_thread_completion():
        """Scan given inputs, update associated ui, and save scan data"""
        scan_start_date = datetime.datetime.now()
        update_left_header_label("Scan in process...")
        scan_button.config(state="disabled")
        waiting_scanner1 = STimer.do_after(
            update_left_header_label_random_waiting_msg, 15)
        waiting_scanner2 = STimer.do_after(
            update_left_header_label_random_waiting_msg, 30)
        waiting_scanner3 = STimer.do_after(
            update_left_header_label_random_waiting_msg, 45)

        ports = f'{port_start_entry_var.get()}-{port_end_entry_var.get()}'
        hosts = scan_host_entry_var.get()
        scanner = Scanner(hosts, ports)

        set_host(scanner.get_scan_details(System.Settings.get_scan_type()))
        set_cpes_vulns(scanner.get_cpes())

        scan_button.config(state="normal")
        scan_details_view.check_vulnerabilities_button.config(state="normal")

        scan_end_date = datetime.datetime.now()
        timedelta = scan_end_date - scan_start_date
        timedelta.total_seconds()

        last_row_id = df.DBFunctions.save_scan(scan_start_date,
                                               timedelta.total_seconds())

        for host in get_hosts():
            df.DBFunctions.save_host(host, last_row_id)

        query = "SELECT * FROM Hosts WHERE ScanID = ?"
        host_tuple = df.DBFunctions.get_all_where(query, (last_row_id, ))
        hosts_with_ID = []

        for id_host in host_tuple:
            temp = Host(id_host[0], id_host[1], "Old Host", id_host[5],
                        id_host[3], id_host[4], id_host[6], id_host[2])
            hosts_with_ID.append(temp)

        set_host(hosts_with_ID)

        ip_list = [*DataShare.get_cpes()]
        cpe_list = DataShare.get_cpes()

        for ip in ip_list:
            for item in hosts_with_ID:
                if item.get_ip() == ip:
                    cpe_list[item.get_id()] = cpe_list.pop(ip)

        DataShare.set_cpes(cpe_list)
        cves_with_host = df.DBFunctions.query_cves(cpe_list)

        for i in cves_with_host:
            for j in i:
                df.DBFunctions.save_cve_by_host(i, j)

        update_left_header_label(f"Scan finished in {timedelta} seconds")
        STimer.do_after(reset_left_header_label, 2)
        waiting_scanner1.cancel()
        waiting_scanner2.cancel()
        waiting_scanner3.cancel()

    def set_host(h):
        """Set scanned hosts for ui
        :param h: hosts found
        """
        if h:
            DataShare.set_hosts(h)
            reload_hosts_tableview()

    def get_hosts():
        """Get scanned hosts"""
        return DataShare.get_hosts()

    def set_cpes_vulns(c):
        """Set vulnerabilities from cps"""
        print("Main 172 set_cpes_vulns   cpes:\n")
        print(c)
        DataShare.set_cpes(c)

        # Sort according to the Vulnerability Sort Setting
        reverse_sort = False

        if System.Settings.get_vuln_sort_type() == System.SortType.alphaDESC:
            reverse_sort = True

        sorted_vulns = sorted(df.DBFunctions.query_cves(c),
                              reverse=reverse_sort)
        print('From Main 184, sorted_vulns: ', sorted_vulns)
        DataShare.set_vulns(sorted_vulns)
        # reload ui

    # Click Handlers
    def on_scan():
        """Click handler for scan btn to start scanner thread"""
        # MAKE SURE TO VALIDATE INPUT
        scan_thread = SThread(0, "SCAN_THREAD_1", 5, scan_thread_completion)
        scan_thread.start()

    def on_select_scan(id):
        query = "SELECT * FROM Hosts WHERE ScanID = ?"
        params = (id, )

        data = df.DBFunctions.get_all_where(query, params)
        test = df.DBFunctions.retrieve_scanID_data(id)
        print('\n\n\n\nGetting Data\n')
        print(data)
        print('\n')
        print(test)
        # these need to be set, but not sure if the cpes and vulns are differentiate
        # by scans like hosts are
        # todo: set cpes and vulns in DataShare
        print('\n\n\n\nCPES')
        #todo this changes depending on if a scan has been run
        print(DataShare.get_cpes())
        print('\n\nVULNS')
        #todo these are 2.2 cpes...
        print(DataShare.get_vulns())
        print('\n\n\n\n')

        curr_hosts = []
        # for each host scanned
        for host_raw in data:
            host_id = host_raw[0]

            ip = host_raw[1]
            state = "Old Host"
            mac = host_raw[2]
            os_gen = host_raw[3]
            os_family = host_raw[4]
            name = host_raw[5]
            vendor = host_raw[6]

            curr_hosts.append(
                Host(host_id, ip, state, name, os_family, os_gen, vendor, mac))

        set_host(curr_hosts)

    def find_exploit(cve):
        if cve:
            if exploit_view:
                exploit_view.update_cve(cve)
        else:
            print('No CVE selected')

    def update_exploit_tab(cve):
        main_note_book.select(2)
        exploit_view.cve_var.set(cve)
        exploit_view.on_search()

    def on_host_tableview_select(event):
        """Click handler to update right ui when user clicks on a host in left box"""
        index = hosts_table_view.get_selected_index()
        hosts = DataShare.get_hosts()

        scan_details_view.host_name_entry_var.set(
            hosts[index].get_display_name())
        scan_details_view.mac_address_entry_var.set(
            hosts[index].get_mac_address())
        scan_details_view.port_number_entry_var.set(hosts[index].get_ip())

    def donothing():
        filewin = Toplevel(root)
        button = Button(filewin, text="Do nothing button")
        button.pack()

    def update_import():
        # Only takes json currently. path = askopenfilename(title='Select Database file to import...',
        # defaultextension='.db', filetypes=(("database files", "*.db"),("datafeeds", "*.json"),("all files", "*.*")))

        path = askopenfilename(title='Select Database file to import...',
                               filetypes=[('Json', '*.json')])

        # ntpath for os compatibility with differing separators
        # head and tail if path ends in backslash
        head, tail = ntpath.split(path)
        fname = tail or ntpath.basename(head)

        if fname.endswith('.json'):
            # for use to support multiple file types
            # elif json_fp.endswith(('.json', '.db', '.xml'):
            df.DBFunctions.import_NVD_JSON(fname)
        else:
            tk.messagebox.showerror("Error", "File must be of type: json")

    # Set up tree columns to display IP and Device Names after a completed scan
    class TreeColumns(enum.Enum):
        name = 0
        mac_address = 1

        @staticmethod
        def display_name_for_column(col):
            display_names = {
                0: "IP",
                1: "Name",
            }
            return display_names[col]

        @staticmethod
        def all_cases():
            cases = []

            for col in TreeColumns:
                cases.append(TreeColumns.display_name_for_column(col.value))

            return cases

    # Setup root ui

    root = ThemedTk()
    root.ttkStyle = ThemedStyle()
    theme = System.Settings.get_theme()
    root.ttkStyle.set_theme(theme)
    root.title("AnyScan")
    root.grid_rowconfigure(0, weight=1)
    root.grid_columnconfigure(1, weight=1)

    #################
    # Setup LeftFrame
    #################
    left_frame = ttk.Frame(root)
    left_frame.grid(row=0, column=0, sticky="nsew")
    left_frame.grid_rowconfigure(1, weight=1)
    left_frame.grid_columnconfigure(1, weight=1)

    # Setup Left Frame header Label
    left_frame_header_label_var = tk.StringVar()
    update_left_header_label(None)
    left_frame_header_label = ttk.Label(
        left_frame, textvariable=left_frame_header_label_var)
    left_frame_header_label.grid(row=0, column=0)

    # Setup Left Frame Host TableView
    sections_tuple = TreeColumns.all_cases()
    data = []
    hosts_table_view = TableView(left_frame, 1, sections_tuple, data)
    hosts_table_view.bind_method('<ButtonRelease-1>', on_host_tableview_select)
    reload_hosts_tableview()

    # Setup scan host frame
    scan_host_frame = ttk.Frame(left_frame)
    scan_host_frame.grid(row=2, column=0)

    # Setup scan host label
    scan_host_label = ttk.Label(scan_host_frame, text="Hosts:")
    scan_host_label.grid(row=0, column=0)

    # Setup scan host entry
    scan_host_entry_var = tk.StringVar()
    scan_host_entry_var.set("192.168.1.0/28")
    scan_host_entry = ttk.Entry(scan_host_frame,
                                textvariable=scan_host_entry_var)
    scan_host_entry.grid(row=0, column=1)

    # Setup scan port label frame
    scan_port_label_frame = ttk.Frame(left_frame)
    scan_port_label_frame.grid(row=3, column=0)

    # Setup scan port label
    port_start_label = ttk.Label(scan_port_label_frame, text="Start Port")
    port_start_label.grid(row=0, column=0, padx=(0, 8))
    port_end_label = ttk.Label(scan_port_label_frame, text="End Port")
    port_end_label.grid(row=0, column=1, padx=(8, 0))

    # Setup scan port frame
    scan_port_frame = ttk.Frame(left_frame)
    scan_port_frame.grid(row=4, column=0)

    # Setup scan port entries
    port_start_entry_var = tk.StringVar()
    port_start_entry_var.set("21")
    port_start_entry = ttk.Entry(scan_port_frame,
                                 width=4,
                                 textvariable=port_start_entry_var)
    port_start_entry.grid(row=0, column=0, padx=(0, 16))

    port_end_entry_var = tk.StringVar()
    port_end_entry_var.set("30")
    port_end_entry = ttk.Entry(scan_port_frame,
                               width=4,
                               textvariable=port_end_entry_var)
    port_end_entry.grid(row=0, column=1, padx=(16, 0))

    scan_button_frame = ttk.Frame(left_frame)
    scan_button_frame.grid(row=5, column=0)

    # Setup Left frame scan button
    scan_button = ttk.Button(scan_button_frame, text="Scan", command=on_scan)

    scan_button.grid(row=0, column=0, pady=(8, 8))

    #################
    # Setup RightFrame
    #################

    # Setup Notebook for right frame
    rows = 0
    while rows < 50:
        root.columnconfigure(rows + 1, weight=1)
        rows += 1

    # Setup Root Notebook
    main_note_book = ttk.Notebook(root)

    main_note_book.grid(row=0,
                        column=1,
                        columnspan=50,
                        rowspan=49,
                        sticky="NESW")

    # Setup Scan Details Tab
    scan_details_view = ScanDetailsView()
    scan_details_tab = scan_details_view.get_view(main_note_book)
    main_note_book.add(scan_details_tab, text="Scan Details")

    # Setup Vulnerabilities Tab
    vulnerabilities_view = VulnerabilitiesView()
    vulnerabilities_tab = vulnerabilities_view.get_view(main_note_book)
    main_note_book.add(vulnerabilities_tab, text="Vulnerabilities")
    vulnerabilities_view.on_selected_cve = find_exploit
    vulnerabilities_view.move_to_exploit = update_exploit_tab

    # Setup Exploits Tab
    exploit_view = ExploitView()
    exploit_tab = exploit_view.get_view(main_note_book)
    main_note_book.add(exploit_tab, text='Exploits')

    # Setup Scan History Tab
    scan_history_view = ScanHistoryView()
    scan_history_tab = scan_history_view.get_view(main_note_book)
    main_note_book.add(scan_history_tab, text="Scan History")
    scan_history_view.on_selected_scan_completion = on_select_scan

    # File Menu Bar
    menubar = Menu(root)  # create menu bar
    filemenu = Menu(menubar, tearoff=0)  # create a menu to add some stuff too

    # Save Vulnerability in file menu bar
    savemenu = Menu(menubar, tearoff=0)
    savemenu.add_command(label="Save Vulnerability",
                         command=VulnPopup.new_popup)
    filemenu.add_cascade(label='Save', menu=savemenu)

    # DB import in file menu bar
    importmenu = Menu(menubar, tearoff=0)
    importmenu.add_command(label="Database", command=update_import)
    filemenu.add_cascade(label="Import", menu=importmenu)
    filemenu.add_separator()  # more prettiness

    # Scan settings in file menu bar
    settingsmenu = Menu(menubar, tearoff=0)
    settingsmenu.add_command(label="Scan Settings",
                             command=scan_details_view.on_settings)
    filemenu.add_cascade(label='Settings', menu=settingsmenu)
    filemenu.add_separator()  # pretty

    # Helper method to change application themes
    def change_theme(theme):
        root.ttkStyle.set_theme(theme)
        System.Settings.set_theme(theme)

    # Added the ability for the user to change themes from the cascading file menu
    themes_menu = Menu(menubar, tearoff=0)
    themes_menu.add_command(label="Alt", command=lambda: change_theme("alt"))
    themes_menu.add_command(label="Aqua", command=lambda: change_theme("aqua"))
    themes_menu.add_command(label="Clam", command=lambda: change_theme("clam"))
    themes_menu.add_command(label="Classic",
                            command=lambda: change_theme("classic"))
    themes_menu.add_command(label="Default",
                            command=lambda: change_theme("default"))
    themes_menu.add_command(label="Equilux",
                            command=lambda: change_theme("equilux"))
    themes_menu.add_separator()
    themes_menu.add_command(label="Scidblue",
                            command=lambda: change_theme("scidblue"))
    themes_menu.add_command(label="Scidgreen",
                            command=lambda: change_theme("scidgreen"))
    themes_menu.add_command(label="Scidgrey",
                            command=lambda: change_theme("scidgrey"))
    themes_menu.add_command(label="Scidmint",
                            command=lambda: change_theme("scidmint"))
    themes_menu.add_command(label="Scidpink",
                            command=lambda: change_theme("scidpink"))
    themes_menu.add_command(label="Scidpurple",
                            command=lambda: change_theme("scidpurple"))
    themes_menu.add_command(label="Scidsand",
                            command=lambda: change_theme("scidsand"))

    filemenu.add_cascade(label='Change Theme', menu=themes_menu)
    filemenu.add_separator()
    filemenu.add_command(label="Exit", command=root.quit)

    editmenu = Menu(menubar,
                    tearoff=0)  # create another menu to add some stuff too
    editmenu.add_command(label="Undo", command=donothing)

    menubar.add_cascade(label="File", menu=filemenu)  # add file to menu bar
    # On macOS there are some default things added to this menu, but are not added to the same menu
    # under File.
    menubar.add_cascade(label='Edit',
                        menu=editmenu)  # add edit to menu bar too, for fun

    # Run the program with UI
    root.config(menu=menubar)
    root.geometry("1600x1000")
    root.minsize(800, 500)
    # add this to ensure app comes to front on start up
    root.lift()
    root.attributes('-topmost', True)
    root.after_idle(root.attributes, '-topmost', False)
    # start GUI
    root.mainloop()
Example #2
0
    window.resizable(False, False)

    # Personnalisation Style
    style = Style(window)
    original_font = font.nametofont(style.lookup("TLabel", "font"))
    f = font.Font(**original_font.configure())
    f.configure(weight='bold', underline=0, size=9)
    style.configure('H1.TLabel', font=f)
    original_font = font.nametofont(style.lookup("TButton", "font"))

    f2 = font.Font(**original_font.configure())
    f2.configure(weight='bold', size=9)
    style.configure('H1.TButton', font=f2)

    window.grid_columnconfigure(0, weight=1)
    window.grid_rowconfigure(0, weight=1)
    window.minsize(MIN_WIDTH, MIN_HEIGHT)

    # FRAME Principale
    frame_principale = Frame(window)
    frame_principale.grid_columnconfigure(0, weight=1)
    frame_principale.grid_rowconfigure(0, weight=1)
    frame_principale.grid(sticky='NSEW')

    label_fonct = Label(frame_principale, text='Fonctionnel', style='H1.TLabel')
    bouton_lancer = Button(frame_principale, text="Incrémenter dates XML", command=ouvrir_incrementeur_date)
    bouton_dl_visualiseur = Button(frame_principale, text="installation visualiseur d'offres", command=installer_visualiseur)
    label_java = Label(frame_principale, text='Code Java', style='H1.TLabel')
    bouton_lancer_traque = Button(frame_principale, text="Vérifier clés messages", command=ouvrir_traque_mes_cles)
    label_version = Label(frame_principale, text="v" + __version__, font=('Arial', 8), anchor='se')
Example #3
0
# create the listbox of lines
lbox = Listbox(root, listvariable=names, selectmode="browse", height=10)
lbox.bind("<<ListboxSelect>>", updateSelection)

# colorize alternating lines of the listbox
for i in range(0,len(nlist),2):
    lbox.itemconfigure(i, background='#EAEAEA')

# create the scrollbar
sbar = ttk.Scrollbar(root, orient=VERTICAL, command=lbox.yview)
lbox.configure(yscrollcommand=sbar.set)

# create the selection label
label = ttk.Label(root, textvariable=display)

# palce the widgets
lbox.grid(column=0, row=0, sticky=(N,E,S,W))
sbar.grid(column=1, row=0, sticky=(N,S))
label.grid(column=0, row=1)

# configure grid
root.grid_columnconfigure(0, weight=1)
root.grid_rowconfigure(0, weight=1)

# setup a sizegrip item at the bottom right corner
ttk.Sizegrip().grid(column=1, row=1, sticky=(S,E))

# loop
root.mainloop()