static void apply_hosts_preferences (openvas_hosts_t *hosts, struct arglist *preferences) { char *ordering, *exclude_hosts; if (hosts == NULL || preferences == NULL) return; /* Hosts ordering strategy: sequential, random, reversed... */ ordering = preferences_get_string (preferences, "hosts_ordering"); if (ordering) { if (!strcmp (ordering, "random")) { openvas_hosts_shuffle (hosts); log_write ("hosts_ordering: Random.\n"); } else if (!strcmp (ordering, "reverse")) { openvas_hosts_reverse (hosts); log_write ("hosts_ordering: Reverse.\n"); } } else log_write ("hosts_ordering: Sequential.\n"); /* Exclude hosts ? */ exclude_hosts = preferences_get_string (preferences, "exclude_hosts"); if (exclude_hosts) { /* Exclude hosts, resolving hostnames. */ int ret = openvas_hosts_exclude (hosts, exclude_hosts, 1); if (ret >= 0) log_write ("exclude_hosts: Skipped %d host(s).\n", ret); else log_write ("exclude_hosts: Error.\n"); } /* Reverse-lookup unify ? */ if (preferences_get_bool (preferences, "reverse_lookup_unify") == 1) log_write ("reverse_lookup_unify: Skipped %d host(s).\n", openvas_hosts_reverse_lookup_unify (hosts)); /* Hosts that reverse-lookup only ? */ if (preferences_get_bool (preferences, "reverse_lookup_only") == 1) log_write ("reverse_lookup_only: Skipped %d host(s).\n", openvas_hosts_reverse_lookup_only (hosts)); }
static void add_general_tag (char* tag_name, Preference text_pref, Preference background_pref, Preference font_pref) { GdkRGBA *fg_color, *bg_color; char *font; char *key; /* initialize tag preferences */ /* text color */ key = preferences_get_key (text_pref); fg_color = preferences_get_color (key); preferences_notify_add (key, changed_text, tag_name); g_free (key); /* base color */ key = preferences_get_key (background_pref); bg_color = preferences_get_color (key); preferences_notify_add (key, changed_background, tag_name); g_free (key); /* font */ key = preferences_get_key (font_pref); font = preferences_get_string (key); preferences_notify_add (key, changed_font, tag_name); g_free (key); highlight_add_tag (tag_name, fg_color, bg_color, font); }
/* * Applies the source_iface scanner preference, if allowed by ifaces_allow and * ifaces_deny preferences. * * @return 0 if source_iface preference applied or not found, -1 if * unauthorized value, -2 if iface can't be used. */ static int apply_source_iface_preference (struct arglist *globals, struct arglist *preferences) { char *source_iface; int ret; source_iface = preferences_get_string (preferences, "source_iface"); if (source_iface == NULL) return 0; ret = iface_authorized (source_iface, preferences); if (ret == -1) { gchar *msg = g_strdup_printf ("Unauthorized source interface: %s", source_iface); log_write ("source_iface: Unauthorized source interface %s.\n", source_iface); error_message_to_client (globals, msg, NULL, NULL); g_free (msg); return -1; } else if (ret == -2) { gchar *msg = g_strdup_printf ("Unauthorized source interface: %s" " (system-wide restriction.)", source_iface); log_write ("source_iface: Unauthorized source interface %s." " (sys_* preference restriction.)\n", source_iface); error_message_to_client (globals, msg, NULL, NULL); g_free (msg); return -1; } if (openvas_source_iface_init (source_iface)) { gchar *msg = g_strdup_printf ("Erroneous source interface: %s", source_iface); log_write ("source_iface: Error with %s interface.\n", source_iface); error_message_to_client (globals, msg, NULL, NULL); g_free (msg); return -2; } else { char *ipstr, *ip6str; ipstr = openvas_source_addr_str (); ip6str = openvas_source_addr6_str (); log_write ("source_iface: Using %s (%s / %s).\n", source_iface, ipstr, ip6str); g_free (ipstr); g_free (ip6str); return 0; } }
static void init_file (char *name, Preference pref) { GtkWidget *widget; char *sval; widget = glade_xml_get_widget (warlock_xml, name); sval = preferences_get_string (preferences_get_key (pref)); debug("sval: %s\n", sval); if (sval != NULL) { // if we got a relative path, make it relative to home dir if (!g_path_is_absolute (sval)) { char *tmp; tmp = sval; sval = g_build_filename (g_get_user_data_dir (), sval, NULL); g_free (tmp); } assure_directory (sval); gtk_file_chooser_set_filename (GTK_FILE_CHOOSER (widget), sval); } g_signal_connect (G_OBJECT (widget), "selection_changed", G_CALLBACK (on_path_filechooserbutton_selection_changed), GINT_TO_POINTER (pref)); }
static void init_font (char *name, Preference pref) { GtkWidget *widget; GtkWidget *box; const char *sval; char *key; box = glade_xml_get_widget (warlock_xml, name); widget = warlock_font_button_new (); gtk_box_pack_start (GTK_BOX (box), widget, FALSE, TRUE, 0); gtk_box_reorder_child (GTK_BOX (box), widget, 0); key = preferences_get_key (pref); sval = preferences_get_string (key); if (sval != NULL) { warlock_font_button_set_font_name (WARLOCK_FONT_BUTTON (widget), sval); } g_free (key); g_signal_connect (widget, "font-set", G_CALLBACK (on_font_button_font_set), GINT_TO_POINTER (pref)); gtk_widget_show (widget); }
GdkColor *preferences_get_color (const char *key) { char *str; str = preferences_get_string (key); return gdk_color_from_string (str); }
static void highlight_add (guint id) { WarlockHighlight *highlight; const char *string; gboolean case_sensitive; guint i; char *name; string = preferences_get_string (preferences_get_highlight_key (id, PREF_HIGHLIGHT_STRING)); case_sensitive = preferences_get_bool (preferences_get_highlight_key (id, PREF_HIGHLIGHT_CASE_SENSITIVE)); highlight = g_new (WarlockHighlight, 1); highlight->id = id; highlight->regex = highlight_compile_regex (string, case_sensitive); highlight->gconf_connections = NULL; highlight_list = g_slist_append (highlight_list, highlight); highlight_add_tags (id); highlight->gconf_connections = g_slist_append (highlight->gconf_connections, GINT_TO_POINTER (preferences_notify_add (preferences_get_highlight_key (id, PREF_HIGHLIGHT_STRING), change_string, highlight))); highlight->gconf_connections = g_slist_append (highlight->gconf_connections, GINT_TO_POINTER (preferences_notify_add (preferences_get_highlight_key (id, PREF_HIGHLIGHT_CASE_SENSITIVE), change_string, highlight))); for (i = 0; i < HIGHLIGHT_MATCHES; i++) { name = mangle_name (id, i); highlight->gconf_connections = g_slist_append (highlight->gconf_connections, GINT_TO_POINTER (preferences_notify_add (preferences_get_highlight_match_key (id, i, PREF_HIGHLIGHT_MATCH_TEXT_COLOR), changed_text, name))); highlight->gconf_connections = g_slist_append (highlight->gconf_connections, GINT_TO_POINTER (preferences_notify_add (preferences_get_highlight_match_key (id, i, PREF_HIGHLIGHT_MATCH_BASE_COLOR), changed_background, name))); highlight->gconf_connections = g_slist_append (highlight->gconf_connections, GINT_TO_POINTER (preferences_notify_add (preferences_get_highlight_match_key (id, i, PREF_HIGHLIGHT_MATCH_FONT), changed_font, name))); } }
static void init_ssl_ctx (const char *priority, const char *dhparams) { if (openvas_SSL_init () < 0) { log_write ("Could not initialize openvas SSL!\n"); exit (1); } /* Only initialize ovas_scanner_ctx once */ if (ovas_scanner_ctx == NULL) { char *cert, *key, *passwd, *ca_file; ca_file = preferences_get_string (global_preferences, "ca_file"); if (ca_file == NULL) { log_write ("Missing ca_file - Did you run openvas-mkcert?\n"); exit (1); } cert = preferences_get_string (global_preferences, "cert_file"); if (cert == NULL) { log_write ("Missing cert_file - Did you run openvas-mkcert?\n"); exit (1); } key = preferences_get_string (global_preferences, "key_file"); if (key == NULL) { log_write ("Missing key_file - Did you run openvas-mkcert?\n"); exit (1); } passwd = preferences_get_string (global_preferences, "pem_password"); ovas_scanner_ctx = ovas_scanner_context_new (OPENVAS_ENCAPS_TLScustom, cert, key, passwd, ca_file, priority, dhparams); if (!ovas_scanner_ctx) { log_write ("Could not create ovas_scanner_ctx\n"); exit (1); } } }
EXPORT void on_execute_menu_item_activate (GtkMenuItem *menuitem, gpointer user_data) { GtkWidget *file_chooser; GtkFileFilter *wizard_filter, *all_filter; int response; char *script_path; char *key; file_chooser = gtk_file_chooser_dialog_new ("Select script to run", GTK_WINDOW (warlock_get_widget ("main_window")), GTK_FILE_CHOOSER_ACTION_OPEN, GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, GTK_STOCK_OPEN, GTK_RESPONSE_ACCEPT, NULL); key = preferences_get_key (PREF_SCRIPT_PATH); script_path = preferences_get_string (key); gtk_file_chooser_set_current_folder (GTK_FILE_CHOOSER (file_chooser), script_path); g_free (script_path); g_free (key); wizard_filter = gtk_file_filter_new (); gtk_file_filter_set_name (wizard_filter, "Wizard Scripting files"); gtk_file_filter_add_pattern (wizard_filter, "*.[Cc][Mm][Dd]"); gtk_file_filter_add_pattern (wizard_filter, "*.[Ww][Ii][Zz]"); gtk_file_chooser_add_filter (GTK_FILE_CHOOSER (file_chooser), wizard_filter); all_filter = gtk_file_filter_new (); gtk_file_filter_set_name (all_filter, "All files"); gtk_file_filter_add_pattern (all_filter, "*"); gtk_file_chooser_add_filter (GTK_FILE_CHOOSER (file_chooser), all_filter); response = gtk_dialog_run (GTK_DIALOG (file_chooser)); if (response == GTK_RESPONSE_ACCEPT) { char *filename; filename = gtk_file_chooser_get_filename (GTK_FILE_CHOOSER (file_chooser)); script_load (filename, 0, NULL); g_free (filename); } gtk_widget_destroy (file_chooser); }
PangoFontDescription *preferences_get_font (const char *key) { char *str; PangoFontDescription *font; str = preferences_get_string (key); if (str == NULL) { return NULL; } font = pango_font_description_from_string (str); return font; }
static void change_string (const char *key, gpointer user_data) { gboolean case_sensitive; char *string; WarlockHighlight *highlight; highlight = user_data; string = preferences_get_string (preferences_get_highlight_key (highlight->id, PREF_HIGHLIGHT_STRING)); case_sensitive = preferences_get_bool (preferences_get_highlight_key (highlight->id, PREF_HIGHLIGHT_CASE_SENSITIVE)); highlight->regex = highlight_compile_regex (string, case_sensitive); }
/* * Checks if a network interface is authorized to be used as source interface. * * @return 0 if iface is NULL, -1 if unauthorized by ifaces_deny/ifaces_allow, * -2 if by sys_ifaces_deny/sys_ifaces_allow, 1 otherwise. */ static int iface_authorized (const char *iface, struct arglist *preferences) { const char *ifaces_list; if (iface == NULL) return 0; ifaces_list = preferences_get_string (preferences, "ifaces_deny"); if (ifaces_list && str_in_comma_list (iface, ifaces_list)) return -1; ifaces_list = preferences_get_string (preferences, "ifaces_allow"); if (ifaces_list && !str_in_comma_list (iface, ifaces_list)) return -1; /* sys_* preferences are similar, but can't be overriden by the client. */ ifaces_list = preferences_get_string (preferences, "sys_ifaces_deny"); if (ifaces_list && str_in_comma_list (iface, ifaces_list)) return -2; ifaces_list = preferences_get_string (preferences, "sys_ifaces_allow"); if (ifaces_list && !str_in_comma_list (iface, ifaces_list)) return -2; return 1; }
static void changed_font (const char *key, gpointer user_data) { GtkTextTag *tag; char *font; char *name; name = user_data; tag = gtk_text_tag_table_lookup (highlight_tag_table, name); g_assert (tag != NULL); font = preferences_get_string (key); g_object_set (G_OBJECT (tag), "font", font, NULL); g_free (font); }
EXPORT void on_save_history_activate (GtkMenuItem *menuitem, gpointer user_data) { char *name, *log_path, *filename; name = warlock_log_get_name (); log_path = preferences_get_string (preferences_get_key (PREF_LOG_PATH)); filename = g_build_filename (log_path, name, NULL); save_log (filename); g_free (filename); g_free (name); g_free (log_path); }
static void init_entry (char *name, Preference pref) { GtkWidget *widget; char *sval; widget = glade_xml_get_widget (warlock_xml, name); sval = preferences_get_string (preferences_get_key (pref)); if (sval != NULL) { gtk_entry_set_text (GTK_ENTRY (widget), sval); } g_signal_connect (G_OBJECT (widget), "changed", G_CALLBACK (on_entry_changed), GINT_TO_POINTER (pref)); }
EXPORT void on_save_history_as_activate (GtkMenuItem *menuitem, gpointer user_data) { GtkWidget *dialog; char *log_path, *name, *key; dialog = gtk_file_chooser_dialog_new ("Save File", GTK_WINDOW (glade_xml_get_widget (warlock_xml, "main_window")), GTK_FILE_CHOOSER_ACTION_SAVE, GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, GTK_STOCK_SAVE, GTK_RESPONSE_ACCEPT, NULL); gtk_file_chooser_set_do_overwrite_confirmation (GTK_FILE_CHOOSER (dialog), TRUE); key = preferences_get_key (PREF_LOG_PATH); log_path = preferences_get_string (key); g_free (key); (void)gtk_file_chooser_set_current_folder (GTK_FILE_CHOOSER (dialog), log_path); g_free (log_path); name = warlock_log_get_name (); gtk_file_chooser_set_current_name (GTK_FILE_CHOOSER (dialog), name); g_free (name); if (gtk_dialog_run (GTK_DIALOG (dialog)) == GTK_RESPONSE_ACCEPT) { char *filename; filename = gtk_file_chooser_get_filename (GTK_FILE_CHOOSER (dialog)); save_log (filename); g_free (filename); } gtk_widget_destroy (dialog); }
// to be called at program start and anytime the value of auto-log changes static void log_toggle (void) { char *key; gboolean autolog; key = preferences_get_key (PREF_AUTO_LOG); autolog = preferences_get_bool (key); g_free (key); if (autolog && log_file == NULL) { GError *err; char *filename, *name, *path, *path_key; path_key = preferences_get_key (PREF_LOG_PATH); path = preferences_get_string (path_key); g_free (path_key); name = warlock_log_get_name (); filename = g_build_filename (path, name, NULL); g_free (name); g_free (path); err = NULL; log_file = g_io_channel_new_file (filename, "a", &err); if (log_file == NULL) { echo_f ("Error: \"%s\" for file \"%s\".\n", err->message, filename); } } else if (!autolog && log_file != NULL) { g_io_channel_close (log_file); g_io_channel_unref (log_file); log_file = NULL; } }
static void highlight_add_tags (guint id) { /* * don't call this function if you think there might be a tag by this * name already, call highlight_check_tags first if that's the case */ int i; for (i = 0; i < HIGHLIGHT_MATCHES; i++) { GdkRGBA *text, *background; char *font; text = preferences_get_color ( preferences_get_highlight_match_key (id, i, PREF_HIGHLIGHT_MATCH_TEXT_COLOR)); background = preferences_get_color ( preferences_get_highlight_match_key (id, i, PREF_HIGHLIGHT_MATCH_BASE_COLOR)); font = preferences_get_string ( preferences_get_highlight_match_key (id, i, PREF_HIGHLIGHT_MATCH_FONT)); highlight_add_tag (mangle_name (id, i), text, background, font); } }
/** * @brief Attack a whole network. */ void attack_network (struct arglist *globals) { int max_hosts = 0, max_checks; int num_tested = 0; char *hostlist; openvas_hosts_t *hosts, *hosts_allow, *hosts_deny; openvas_hosts_t *sys_hosts_allow, *sys_hosts_deny; openvas_host_t *host; int global_socket = -1; struct arglist *preferences = NULL; struct arglist *plugins = NULL; plugins_scheduler_t sched; int fork_retries = 0; GHashTable *files; struct timeval then, now; char buffer[INET6_ADDRSTRLEN]; int network_phase = 0; gchar *network_targets, *port_range; int do_network_scan = 0; int scan_stopped; gettimeofday (&then, NULL); preferences = arg_get_value (globals, "preferences"); if ((do_network_scan = preferences_get_bool (preferences, "network_scan")) == -1) do_network_scan = 0; network_targets = arg_get_value (preferences, "network_targets"); if (network_targets != NULL) arg_add_value (globals, "network_targets", ARG_STRING, strlen (network_targets), network_targets); if (do_network_scan) { gchar *network_scan_status = arg_get_value (globals, "network_scan_status"); if (network_scan_status != NULL) if (g_ascii_strcasecmp (network_scan_status, "done") == 0) network_phase = 0; else network_phase = 1; else { arg_add_value (globals, "network_scan_status", ARG_STRING, strlen ("busy"), "busy"); network_phase = 1; } } num_tested = 0; global_socket = GPOINTER_TO_SIZE (arg_get_value (globals, "global_socket")); plugins = arg_get_value (globals, "plugins"); /* Init and check Target List */ hostlist = arg_get_value (preferences, "TARGET"); if (hostlist == NULL) { error_message_to_client (globals, "Missing target hosts", NULL, NULL); return; } /* Verify the port range is a valid one */ port_range = arg_get_value (preferences, "port_range"); if (validate_port_range (port_range)) { error_message_to_client (globals, "Invalid port range", NULL, port_range); return; } /* Initialize the attack. */ sched = plugins_scheduler_init (plugins, preferences_get_bool (preferences, "auto_enable_dependencies") == 1 ? 1 : 0, network_phase); max_hosts = get_max_hosts_number (preferences); max_checks = get_max_checks_number (preferences); if (network_phase) { network_targets = arg_get_value (preferences, "network_targets"); if (network_targets == NULL) { log_write ("WARNING: In network phase, but without targets! Stopping.\n"); host = NULL; } else { log_write ("Start a new scan. Target(s) : %s, in network phase with target %s\n", hostlist, network_targets); } } else { log_write ("Starts a new scan. Target(s) : %s, with max_hosts = %d and" " max_checks = %d\n", hostlist, max_hosts, max_checks); } hosts = openvas_hosts_new (hostlist); /* Apply Hosts preferences. */ apply_hosts_preferences (hosts, preferences); /* Don't start if the provided interface is unauthorized. */ if (apply_source_iface_preference (globals, preferences) != 0) { openvas_hosts_free (hosts); error_message_to_client (globals, "Interface not authorized for scanning", NULL, NULL); return; } /* hosts_allow/deny lists. */ hosts_allow = openvas_hosts_new (preferences_get_string (preferences, "hosts_allow")); hosts_deny = openvas_hosts_new (preferences_get_string (preferences, "hosts_deny")); /* sys_* preferences, which can't be overriden by the client. */ sys_hosts_allow = openvas_hosts_new (preferences_get_string (preferences, "sys_hosts_allow")); sys_hosts_deny = openvas_hosts_new (preferences_get_string (preferences, "sys_hosts_deny")); host = openvas_hosts_next (hosts); if (host == NULL) goto stop; hosts_init (global_socket, max_hosts); /* * Start the attack ! */ while (host) { int pid; char *hostname; struct in6_addr host_ip; hostname = openvas_host_value_str (host); if (openvas_host_get_addr6 (host, &host_ip) == -1) { log_write ("Couldn't resolve target %s\n", hostname); error_message_to_client (globals, "Couldn't resolve hostname.", hostname, NULL); g_free (hostname); host = openvas_hosts_next (hosts); continue; } /* Do we have the right to test this host ? */ if (!host_authorized (host, &host_ip, hosts_allow, hosts_deny)) { error_message_to_client (globals, "Host access denied.", hostname, NULL); log_write ("Host %s access denied.", hostname); } else if (!host_authorized (host, &host_ip, sys_hosts_allow, sys_hosts_deny)) { error_message_to_client (globals, "Host access denied" " (system-wide restriction.)", hostname, NULL); log_write ("Host %s access denied (sys_* preference restriction.)", hostname); } else { struct attack_start_args args; int s; char *MAC = NULL; int mac_err = -1; gchar *name; if (preferences_get_bool (preferences, "use_mac_addr") > 0 && v6_is_local_ip (&host_ip)) { mac_err = v6_get_mac_addr (&host_ip, &MAC); if (mac_err > 0) { /* remote host is down */ g_free (hostname); host = openvas_hosts_next (hosts); continue; } } s = hosts_new (globals, hostname); if (s < 0) goto scan_stop; args.globals = globals; memcpy (&args.hostip, &host_ip, sizeof (struct in6_addr)); name = openvas_host_value_str (host); strncpy (args.fqdn, name, sizeof (args.fqdn)); g_free (name); args.host_mac_addr = MAC; args.sched = sched; args.thread_socket = s; forkagain: pid = create_process ((process_func_t) attack_start, &args); if (pid < 0) { fork_retries++; if (fork_retries > MAX_FORK_RETRIES) { /* Forking failed - we go to the wait queue. */ log_write ("fork() failed - %s. %s won't be tested\n", strerror (errno), hostname); efree (&MAC); goto stop; } log_write ("fork() failed - sleeping %d seconds and trying again...\n", fork_retries); fork_sleep (fork_retries); goto forkagain; } hosts_set_pid (hostname, pid); if (network_phase) log_write ("Testing %s (network level) [%d]\n", network_targets, pid); else log_write ("Testing %s (%s) [%d]\n", hostname, inet_ntop (AF_INET6, &args.hostip, buffer, sizeof (buffer)), pid); if (MAC != NULL) efree (&MAC); } num_tested++; if (network_phase) { host = NULL; arg_set_value (globals, "network_scan_status", strlen ("done"), "done"); } else { g_free (hostname); host = openvas_hosts_next (hosts); } } /* Every host is being tested... We have to wait for the processes * to terminate. */ while (hosts_read (globals) == 0) ; log_write ("Test complete"); scan_stop: /* Free the memory used by the files uploaded by the user, if any. */ files = arg_get_value (globals, "files_translation"); if (files) g_hash_table_foreach_remove (files, (GHRFunc) free_uploaded_file, NULL); stop: scan_stopped = GPOINTER_TO_SIZE(arg_get_value (globals, "stop_required")); openvas_hosts_free (hosts); openvas_hosts_free (hosts_allow); openvas_hosts_free (hosts_deny); openvas_hosts_free (sys_hosts_allow); openvas_hosts_free (sys_hosts_deny); plugins_scheduler_free (sched); gettimeofday (&now, NULL); log_write ("Total time to scan all hosts : %ld seconds\n", now.tv_sec - then.tv_sec); if (do_network_scan && network_phase && !scan_stopped) attack_network (globals); return; }