예제 #1
0
static void
update_progress_bar()
{
#ifdef FAKE_PROGRESS_BAR
  int total = 100000;
  int remaining = total - progress_bar_level;
  int addme = 0;
  addme = (5*100*remaining)/total;
  progress_bar_level += addme;
  comm_send_status(Globals, 
		  arg_get_value(Hostinfos, "NAME"), 
  		  "portscan", 
		  progress_bar_level,
		  total);  
 signal(SIGALRM, update_progress_bar);
 
 /* 
  * Update the alarm time
  */
 alarm((progress_bar_level/(total))+4);
#else
 fprintf(stderr, "T =%d/%d\tU=%d/%d\n", 
	 scanned_tcp_ports, total_tcp_ports,
	 scanned_udp_ports, total_udp_ports);
 comm_send_status(Globals, 
		  arg_get_value(Hostinfos, "NAME"), 
  		  "portscan", 
		  scanned_tcp_ports + scanned_udp_ports,
		  total_tcp_ports + total_udp_ports);  
#endif
}
예제 #2
0
tree_cell * nasl_scanner_status(lex_ctxt * lexic)
{
 int current = get_int_local_var_by_name(lexic, "current", -1);
 int total   = get_int_local_var_by_name(lexic, "total", -1); 
 struct arglist * script_infos = lexic->script_infos;
 struct arglist * hostdata = arg_get_value(script_infos, "HOSTNAME");

 if(current != -1 && total != -1)
 {
  struct arglist * globs = arg_get_value(script_infos, "globals");			
      if (globs == NULL) return NULL;
      comm_send_status(globs, arg_get_value(hostdata, "NAME"), "portscan", current, total);
  }
 return FAKE_CELL;
} 
예제 #3
0
/**
 * @brief Attack one host.
 */
static void
attack_host (struct arglist *globals, struct arglist *hostinfos, char *hostname,
             plugins_scheduler_t sched)
{
  /* Used for the status */
  int num_plugs = 0;
  int cur_plug = 1;

  kb_t kb;
  gboolean new_kb = FALSE;
  int forks_retry = 0;
  struct arglist *plugins = arg_get_value (globals, "plugins");
  struct arglist *tmp;

  proctitle_set ("openvassd: testing %s", arg_get_value (hostinfos, "NAME"));

  kb = init_host_kb (globals, hostname, hostinfos, &new_kb);

  num_plugs = get_active_plugins_number (plugins);

  tmp = emalloc (sizeof (struct arglist));
  arg_add_value (tmp, "HOSTNAME", ARG_ARGLIST, -1, hostinfos);

  /* launch the plugins */
  pluginlaunch_init (globals);

  for (;;)
    {
      struct scheduler_plugin *plugin;
      pid_t parent;

      /* Check that our father is still alive */
      parent = getppid ();
      if (parent <= 1 || process_alive (parent) == 0)
        {
          pluginlaunch_stop ();
          return;
        }

      /* Idle if the scan has been paused. */
      if (pause_whole_test)
        {
          /* Let the running NVTs complete. */
          pluginlaunch_wait ();

          /* Send the PAUSE status to the client. */
          if (comm_send_status (globals, hostname, "pause", cur_plug, num_plugs)
              < 0)
            {
              pluginlaunch_stop ();
              goto host_died;
            }

          /* Wait for resume. */
          while (pause_whole_test)
            sleep (1);

          /* Send the RESUME status to the client. */
          if (comm_send_status (globals, hostname, "resume", cur_plug,
                                num_plugs) < 0)
            {
              pluginlaunch_stop ();
              goto host_died;
            }
        }

      plugin = plugins_scheduler_next (sched);
      if (plugin != NULL && plugin != PLUG_RUNNING)
        {
          int e;

        again:
          e = launch_plugin (globals, sched, plugin, hostname, &cur_plug,
                             num_plugs, hostinfos, kb, new_kb);
          if (e < 0)
            {
              /*
               * Remote host died
               */
              if (e == ERR_HOST_DEAD)
                goto host_died;
              else if (e == ERR_CANT_FORK)
                {
                  if (forks_retry < MAX_FORK_RETRIES)
                    {
                      forks_retry++;
                      log_write ("fork() failed - sleeping %d seconds (%s)",
                                 forks_retry, strerror (errno));
                      fork_sleep (forks_retry);
                      goto again;
                    }
                  else
                    {
                      log_write ("fork() failed too many times - aborting");
                      goto host_died;
                    }
                }
            }
        }
      else if (plugin == NULL)
        break;
      else
        pluginlaunch_wait_for_free_process ();
    }

  pluginlaunch_wait ();

host_died:
  comm_send_status (globals, hostname, "attack", num_plugs, num_plugs);
  arg_free (tmp);
  pluginlaunch_stop ();
  plugins_scheduler_free (sched);

  gchar *network_scan_status = arg_get_value (globals, "network_scan_status");
  if (network_scan_status != NULL)
    {
      if (g_ascii_strcasecmp (network_scan_status, "busy") == 0)
        {
          save_kb_close (globals, "network");
        }
    }
  else
    if (new_kb == TRUE)
      save_kb_close (globals, hostname);

}
예제 #4
0
/**
 * @brief Launches a nvt. Respects safe check preference (i.e. does not try
 * @brief destructive nvt if save_checks is yes).
 *
 * Does not launch a plugin twice if !save_kb_replay.
 *
 * @param new_kb  If TRUE, kb is new and shall be saved.
 *
 * @return ERR_HOST_DEAD if host died, ERR_CANT_FORK if forking failed,
 *         0 otherwise.
 */
static int
launch_plugin (struct arglist *globals, plugins_scheduler_t * sched,
               struct scheduler_plugin *plugin, char *hostname, int *cur_plug,
               int num_plugs, struct arglist *hostinfos, kb_t kb,
               gboolean new_kb)
{
  struct arglist *preferences = arg_get_value (globals, "preferences");
  struct arglist *args = plugin->arglist->value;
  nvticache_t *nvticache = (nvticache_t *)arg_get_value (
    arg_get_value (args, "preferences"), "nvticache");
  char name[1024], oid_[100], *oid, *src;
  int optimize = preferences_optimize_test (preferences);
  int category = plugin->category;
  gchar *network_scan_status;
  gboolean network_scan = FALSE;

  oid = arg_get_value (args, "OID");
  if (oid)
    src = nvticache_get_src_by_oid (nvticache, oid);
  else
    return 0;

  strncpy (name, src, sizeof (name) - 1);
  name[sizeof (name) - 1] = '\0';
  g_free (src);

  // we need the oid later on and have many exits, so better
  // store it locally without need to free it.
  strncpy (oid_, oid, sizeof (oid_) - 1);
  oid_[sizeof (oid_) - 1] = '\0';

  network_scan_status = arg_get_value (globals, "network_scan_status");
  if (network_scan_status != NULL)
    if (g_ascii_strcasecmp (network_scan_status, "busy") == 0)
      network_scan = TRUE;

  if (plug_get_launch (args) != LAUNCH_DISABLED || category == ACT_SETTINGS)    /* can we launch it ? */
    {
      char *error;
      static int last_status = 0;

      if (preferences_safe_checks_enabled (preferences)
          && (category == ACT_DESTRUCTIVE_ATTACK || category == ACT_KILL_HOST
              || category == ACT_FLOOD || category == ACT_DENIAL))
        {
          if (preferences_log_whole_attack (preferences))
            log_write
              ("Not launching %s against %s %s (this is not an error)\n",
               plugin->arglist->name, hostname,
               "because safe checks are enabled");
          plugin_set_running_state (plugin, PLUGIN_STATUS_DONE);
          return 0;
        }

      (*cur_plug)++;
      if ((*cur_plug * 100) / num_plugs >= last_status)
        {
          last_status = (*cur_plug * 100) / num_plugs + 2;
          if (comm_send_status
              (globals, hostname, "attack", *cur_plug, num_plugs) < 0)
            {
              /* Could not send our status back to our father -> exit */
              pluginlaunch_stop ();
              return ERR_HOST_DEAD;
            }
        }

      if (network_scan)
        {
          char asc_id[100];

          snprintf (asc_id, sizeof (asc_id), "Launched/%s", oid);

          if (kb_item_get_int (kb, asc_id) > 0)
            {
              if (preferences_log_whole_attack (preferences))
                log_write
                  ("Not launching %s against %s %s (this is not an error)\n",
                   plugin->arglist->name, hostname,
                   "because it has already been launched in the past");
              plugin_set_running_state (plugin, PLUGIN_STATUS_DONE);
              return 0;
            }
          else
            {
              kb_item_add_int (kb, asc_id, 1);
              save_kb_write_int (globals, "network", asc_id, 1);
            }
        }

      /* Do not launch NVT if mandatory key is missing (e.g. an important tool
       * was not found). This is ignored during network wide scanning phases. */
      if (network_scan || mandatory_requirements_met (kb, plugin))
        error = NULL;
      else
        error = "because a mandatory key is missing";

      if (!error
          && (!optimize
              || !(error = requirements_plugin (kb, plugin, preferences))))
        {
          int pid;

          /* Start the plugin */
          pid =
            plugin_launch (globals, sched, plugin, hostinfos, preferences, kb,
                           name);
          if (pid < 0)
            {
              plugin_set_running_state (plugin, PLUGIN_STATUS_UNRUN);
              return ERR_CANT_FORK;
            }

          if (preferences_log_whole_attack (preferences))
            log_write ("Launching %s against %s [%d]\n",
                       plugin->arglist->name, hostname, pid);

          /* Stop the test if the host is 'dead' */
          if (kb_item_get_int (kb, "Host/dead") > 0
              || kb_item_get_int (kb, "Host/ping_failed") > 0)
            {
              log_write ("The remote host (%s) is dead\n", hostname);
              pluginlaunch_stop ();

              if (new_kb == TRUE)
                save_kb_close (globals, hostname);

              if (kb_item_get_int (kb, "Host/ping_failed") > 0)
                save_kb_restore_backup (hostname);

              plugin_set_running_state (plugin, PLUGIN_STATUS_DONE);
              return ERR_HOST_DEAD;
            }
        }
      else                      /* requirements_plugin() failed */
        {
          plugin_set_running_state (plugin, PLUGIN_STATUS_DONE);
          if (preferences_log_whole_attack (preferences))
            log_write
              ("Not launching %s against %s %s (this is not an error)\n",
               plugin->arglist->name, hostname,
               error);
        }
    }                           /* if(plugins->launch) */
  else
    plugin_set_running_state (plugin, PLUGIN_STATUS_DONE);

  return 0;
}