示例#1
0
文件: killall.c 项目: Aspekta/psmisc
int
main (int argc, char **argv)
{
  char *name;
  int sig_num;
  int optc;
  int myoptind;
  struct passwd *pwent = NULL;
  char yt[16];
  char ot[16];

  //int optsig = 0;

  struct option options[] = {
    {"exact", 0, NULL, 'e'},
    {"ignore-case", 0, NULL, 'I'},
    {"process-group", 0, NULL, 'g'},
    {"younger-than", 1, NULL, 'y'},
    {"older-than", 1, NULL, 'o'},
    {"interactive", 0, NULL, 'i'},
    {"list-signals", 0, NULL, 'l'},
    {"quiet", 0, NULL, 'q'},
    {"regexp", 0, NULL, 'r'},
    {"signal", 1, NULL, 's'},
    {"user", 1, NULL, 'u'},
    {"verbose", 0, NULL, 'v'},
    {"wait", 0, NULL, 'w'},
#ifdef WITH_SELINUX
    {"context", 1, NULL, 'Z'},
#endif /*WITH_SELINUX*/
    {"version", 0, NULL, 'V'},
    {0,0,0,0 }};

  /* Setup the i18n */
#ifdef ENABLE_NLS
  setlocale(LC_ALL, "");
  bindtextdomain(PACKAGE, LOCALEDIR);
  textdomain(PACKAGE);
#endif
#ifdef WITH_SELINUX
  security_context_t scontext = NULL;
  regex_t scontext_reg;

  if ( argc < 2 ) usage(NULL); /* do the obvious thing... */
#endif /*WITH_SELINUX*/

  name = strrchr (*argv, '/');
  if (name)
    name++;
  else
    name = *argv;
  sig_num = SIGTERM;


  opterr = 0;
#ifdef WITH_SELINUX
  while ( (optc = getopt_long_only(argc,argv,"egy:o:ilqrs:u:vwZ:VI",options,NULL)) != -1) {
#else
  while ( (optc = getopt_long_only(argc,argv,"egy:o:ilqrs:u:vwVI",options,NULL)) != -1) {
#endif
    switch (optc) {
    case 'e':
      exact = 1;
      break;
    case 'g':
      process_group = 1;
      break;
    case 'y':
      strncpy(yt, optarg, 16);
	  yt[15] = '\0';
      if ( 0 >= (younger_than = parse_time_units(yt) ) )
	    usage(_("Invalid time format"));
      break;
    case 'o':
      strncpy(ot, optarg, 16);
	  ot[15] = '\0';
      if ( 0 >= (older_than = parse_time_units(ot) ) )
	    usage(_("Invalid time format"));
      break;
    case 'i':
      interactive = 1;
      break;
    case 'l':
      list_signals();
      return 0;
      break;
    case 'q':
      quiet = 1;
      break;
    case 'r':
	  reg = 1;
	  break;
    case 's':
	  sig_num = get_signal (optarg, "killall");
      break;
    case 'u':
      if (!(pwent = getpwnam(optarg))) {
        fprintf (stderr, _("Cannot find user %s\n"), optarg);
        exit (1);
      }
      break;
    case 'v':
      verbose = 1;
      break;
    case 'w':
      wait_until_dead = 1;
      break;
    case 'I':
      /* option check is optind-1 but sig name is optind */
      if (strcmp(argv[optind-1],"-I") == 0 || strncmp(argv[optind-1],"--",2) == 0) {
        ignore_case = 1;
      } else {
	      sig_num = get_signal (argv[optind]+1, "killall");
      }
      break;
    case 'V':
      /* option check is optind-1 but sig name is optind */
      if (strcmp(argv[optind-1],"-V") == 0 || strncmp(argv[optind-1],"--",2) == 0) {
        print_version();
        return 0;
      }
	    sig_num = get_signal (argv[optind]+1, "killall");
      break;
#ifdef WITH_SELINUX
    case 'Z': 
      if (is_selinux_enabled()>0) {
	    scontext=optarg;
        if (regcomp(&scontext_reg, scontext, REG_EXTENDED|REG_NOSUB) != 0) {
          fprintf(stderr, _("Bad regular expression: %s\n"), scontext);
          exit (1);
	    }
      } else 
        fprintf(stderr, "Warning: -Z (--context) ignored. Requires an SELinux enabled kernel\n");
      break;
#endif /*WITH_SELINUX*/
    case '?':
      /* Signal names are in uppercase, so check to see if the argv
       * is upper case */
      if (argv[optind-1][1] >= 'A' && argv[optind-1][1] <= 'Z') {
	    sig_num = get_signal (argv[optind-1]+1, "killall");
      } else {
        /* Might also be a -## signal too */
        if (argv[optind-1][1] >= '0' && argv[optind-1][1] <= '9') {
          sig_num = atoi(argv[optind-1]+1);
        } else {
          usage(NULL);
        }
      }
      break;
    }
  }
  myoptind = optind;
#ifdef WITH_SELINUX
  if ((argc - myoptind < 1) && pwent==NULL && scontext==NULL) 
#else
  if ((argc - myoptind < 1) && pwent==NULL)	  
#endif
    usage(NULL);

  if (argc - myoptind > MAX_NAMES) {
    fprintf (stderr, _("killall: Maximum number of names is %d\n"),
	   MAX_NAMES);
    exit (1);
  }
  if (!have_proc_self_stat()) {
    fprintf (stderr, _("killall: %s lacks process entries (not mounted ?)\n"),
		PROC_BASE);
    exit (1);
  }
  argv = argv + myoptind;
  /*printf("sending signal %d to procs\n", sig_num);*/
#ifdef WITH_SELINUX
  return kill_all(sig_num,argc - myoptind, argv, pwent, 
		  		scontext ? &scontext_reg : NULL);
#else  /*WITH_SELINUX*/
  return kill_all(sig_num,argc - myoptind, argv, pwent);
#endif /*WITH_SELINUX*/
}
示例#2
0
int main(int argc, char *argv[])
{
	opt_type opts;
	int sig_number;
#ifdef WITH_IPV6
	int ipv4_only, ipv6_only;
#endif
	unsigned char default_namespace = NAMESPACE_FILE;
	struct device_list *match_devices = NULL;
	struct unixsocket_list *unixsockets = NULL;
	struct mount_list *mounts = NULL;

	dev_t netdev;
	struct ip_connections *tcp_connection_list = NULL;
	struct ip_connections *udp_connection_list = NULL;
#ifdef WITH_IPV6
	struct ip6_connections *tcp6_connection_list = NULL;
	struct ip6_connections *udp6_connection_list = NULL;
#endif
	struct inode_list *match_inodes = NULL;
	struct names *names_head, *this_name, *names_tail;
	int argc_cnt;
    char *current_argv, *option;
    char option_buf[3];
    struct option *optr;
	char *nsptr;
  int skip_argv;

	struct option options[] = {
		{"all", 0, NULL, 'a'},
		{"kill", 0, NULL, 'k'},
		{"interactive", 0, NULL, 'i'},
		{"list-signals", 0, NULL, 'l'},
		{"mount", 0, NULL, 'm'},
		{"ismountpoint", 0, NULL, 'M'},
		{"namespace", 1, NULL, 'n'},
		{"silent", 0, NULL, 's'},
		{"user", 0, NULL, 'u'},
		{"verbose", 0, NULL, 'v'},
		{"version", 0, NULL, 'V'},
#ifdef WITH_IPV6
		{"ipv4", 0, NULL, '4'},
		{"ipv6", 0, NULL, '6'},
#endif
		{ 0, 0, 0, 0 }
	};

#ifdef WITH_IPV6
	ipv4_only = ipv6_only = 0;
#endif
	names_head = this_name = names_tail = NULL;
	opts = 0;
	sig_number = SIGKILL;

#ifdef ENABLE_NLS
	/* Set up the i18n */
	setlocale(LC_ALL, "");
	bindtextdomain(PACKAGE, LOCALEDIR);
	textdomain(PACKAGE);
#endif

	netdev = find_net_dev();
	fill_unix_cache(&unixsockets);

    for (argc_cnt = 1; argc_cnt < argc; argc_cnt++) {
      current_argv = argv[argc_cnt];
      if (current_argv[0] == '-') { /* its an option */
        if (current_argv[1] == '-') { /* its a long option */
          if (current_argv[2] == '\0')  /* -- */
            break;
          /* Parse the long options */
          option = option_buf;
          for (optr = options; optr->name != NULL; optr++) {
            if (strcmp(current_argv+2,optr->name) == 0) {
              sprintf(option_buf, "-%c", (char)optr->val);
              break;
            }
          }
          if (optr->name == NULL) {
			fprintf(stderr, _("%s: Invalid option %s\n"), argv[0],
				current_argv);
			usage(NULL);
          }
        } else {
          option = current_argv;
        }
        skip_argv=0;
        while (*(++option) != '\0' && !skip_argv) { /* skips over the - */
		  switch (*option) {
#ifdef WITH_IPV6
		  case '4':
			ipv4_only = 1;
			break;
		  case '6':
			ipv6_only = 1;
			break;
#endif /* WITH_IPV6 */
		  case 'a':
			opts |= OPT_ALLFILES;
			break;
		  case 'c':
			opts |= OPT_MOUNTS;
			break;
		  case 'f':
			/* ignored */
			break;
		  case 'h':
			usage(NULL);
			break;
		  case 'i':
			opts |= OPT_INTERACTIVE;
			break;
		  case 'k':
			opts |= OPT_KILL;
			break;
		  case 'l':
			list_signals();
			return 0;
		  case 'm':
			opts |= OPT_MOUNTS;
			break;
		  case 'M':
			opts |= OPT_ISMOUNTPOINT;
		    read_proc_mounts(&mounts);
			break;
		  case 'n':
            argc_cnt++;
            if (argc_cnt >= argc) {
              usage(_ ("Namespace option requires an argument."));
              exit(1);;
            }
            skip_argv=1;
            //while(option != '\0') option++;
			if (strcmp(argv[argc_cnt], "tcp") == 0)
				default_namespace = NAMESPACE_TCP;
			else if (strcmp(argv[argc_cnt], "udp") == 0)
				default_namespace = NAMESPACE_UDP;
			else if (strcmp(argv[argc_cnt], "file") == 0)
				default_namespace = NAMESPACE_FILE;
			else
				usage(_("Invalid namespace name"));
			break;
		  case 's':
			opts |= OPT_SILENT;
			break;
		  case 'u':
			opts |= OPT_USER;
			break;
		  case 'v':
			opts |= OPT_VERBOSE;
			break;
		  case 'V':
			print_version();
			return 0;
          default:
            if (isupper(*option) || isdigit(*option)) {
              sig_number = get_signal(current_argv+1, argv[0]);
            skip_argv=1;
              break;
            }
			fprintf(stderr, "%s: Invalid option %c\n", argv[0],
				*option);
			usage(NULL);
			exit(1);
			break;
		  }		/* switch */
	    }			/* while option */
        continue;
      } /* an option */
      /* Not an option, must be a file specification */

		if ((this_name = malloc(sizeof(struct names))) == NULL)
			continue;
		this_name->next = NULL;
		/* try to find namespace spec */
		this_name->name_space = default_namespace;
		if (((nsptr = strchr(current_argv, '/')) != NULL)
		    && (nsptr != current_argv)) {
			if (strcmp(nsptr + 1, "tcp") == 0) {
				this_name->name_space = NAMESPACE_TCP;
				*nsptr = '\0';
			} else if (strcmp(nsptr + 1, "udp") == 0) {
				this_name->name_space = NAMESPACE_UDP;
				*nsptr = '\0';
			} else if (strcmp(nsptr + 1, "file") == 0) {
				this_name->name_space = NAMESPACE_FILE;
				*nsptr = '\0';
			}
		}
		this_name->matched_procs = NULL;
		if (opts & (OPT_MOUNTS|OPT_ISMOUNTPOINT)
		    && this_name->name_space != NAMESPACE_FILE)
			usage(_
			      ("You can only use files with mountpoint options"));
		if (opts & OPT_ISMOUNTPOINT &&
		    !is_mountpoint(&mounts, current_argv)) {
			free(this_name);
			continue;
		}
		switch (this_name->name_space) {
		case NAMESPACE_TCP:
			if (asprintf(&(this_name->filename), "%s/tcp", current_argv) > 0) {
#ifdef WITH_IPV6
			  parse_inet(this_name, ipv4_only, ipv6_only,
				   &tcp_connection_list, &tcp6_connection_list);
#else
			  parse_inet(this_name, &tcp_connection_list);
#endif
			}
			break;
		case NAMESPACE_UDP:
			if (asprintf(&(this_name->filename), "%s/udp", current_argv) > 0) {
#ifdef WITH_IPV6
			  parse_inet(this_name, ipv4_only, ipv6_only,
				   &udp_connection_list, &udp6_connection_list);
#else
			  parse_inet(this_name, &udp_connection_list);
#endif
			}
			break;
		default:	/* FILE */
			this_name->filename = strdup(current_argv);
			if (parse_file(this_name, &match_inodes) == 0) {
              parse_unixsockets(this_name, &match_inodes, unixsockets);
			  if (opts & OPT_MOUNTS)
				parse_mounts(this_name, &match_devices, opts);
            }
			break;
		}

		if (names_head == NULL)
			names_head = this_name;
		if (names_tail != NULL)
			names_tail->next = this_name;
		names_tail = this_name;
    } /* for across the argvs */
	if (names_head == NULL)
		usage(_("No process specification given"));

	if (opts & OPT_SILENT) {
		opts &= ~OPT_VERBOSE;
		opts &= ~OPT_USER;
		if (opts & OPT_ALLFILES)
			usage(_
			      ("all option cannot be used with silent option."));
	}
#ifdef WITH_IPV6
	if (ipv4_only && ipv6_only)
		usage(_
		      ("You cannot search for only IPv4 and only IPv6 sockets at the same time"));
	if (!ipv6_only) {
#endif
		if (tcp_connection_list != NULL)
			find_net_sockets(&match_inodes, tcp_connection_list,
					 "tcp", netdev);
		if (udp_connection_list != NULL)
			find_net_sockets(&match_inodes, udp_connection_list,
					 "udp", netdev);
#ifdef WITH_IPV6
	}
	if (!ipv4_only) {
		if (tcp6_connection_list != NULL)
			find_net6_sockets(&match_inodes, tcp6_connection_list,
					  "tcp", netdev);
		if (udp6_connection_list != NULL)
			find_net6_sockets(&match_inodes, udp6_connection_list,
					  "udp", netdev);
	}
#endif
#ifdef DEBUG
	debug_match_lists(names_head, match_inodes, match_devices);
#endif
	scan_procs(names_head, match_inodes, match_devices, unixsockets,
		   netdev);
	scan_knfsd(names_head, match_inodes, match_devices);
	scan_mounts(names_head, match_inodes, match_devices);
	scan_swaps(names_head, match_inodes, match_devices);
	return print_matches(names_head, opts, sig_number);
}
示例#3
0
int
main (int argc, char **argv)
{
  char *name;
  int sig_num;
  int optc;
  int myoptind;
  struct passwd *pwent = NULL;
  struct stat isproc;
  
  //int optsig = 0;

  struct option options[] = {
    {"exact", 0, NULL, 'e'},
    {"ignore-case", 0, NULL, 'I'},
    {"process-group", 0, NULL, 'g'},
    {"interactive", 0, NULL, 'i'},
    {"list-signals", 0, NULL, 'l'},
    {"quiet", 0, NULL, 'q'},
    {"regexp", 0, NULL, 'r'},
    {"signal", 1, NULL, 's'},
    {"user", 1, NULL, 'u'},
    {"verbose", 0, NULL, 'v'},
    {"wait", 0, NULL, 'w'},
#ifdef WITH_SELINUX
    {"context", 1, NULL, 'Z'},
#endif /*WITH_SELINUX*/
    {"version", 0, NULL, 'V'},
    {0,0,0,0 }};

  /* Setup the i18n */
#ifdef ENABLE_NLS
  setlocale(LC_ALL, "");
  bindtextdomain(PACKAGE, LOCALEDIR);
  textdomain(PACKAGE);
#endif
#ifdef WITH_SELINUX
  security_context_t scontext = NULL;
  regex_t scontext_reg;

  if ( argc < 2 ) usage(); /* do the obvious thing... */
#endif /*WITH_SELINUX*/

  name = strrchr (*argv, '/');
  if (name)
    name++;
  else
    name = *argv;
  pidof = strcmp (name, "killall");
  sig_num = SIGTERM;


  opterr = 0;
#ifdef WITH_SELINUX
  while ( (optc = getopt_long_only(argc,argv,"egilqrs:u:vwZ:VI",options,NULL)) != EOF) {
#else
  while ( (optc = getopt_long_only(argc,argv,"egilqrs:u:vwVI",options,NULL)) != EOF) {
#endif
    switch (optc) {
      case 'e':
        exact = 1;
        break;
      case 'g':
        process_group = 1;
        break;
      case 'i':
        if (pidof)
          usage();
        interactive = 1;
        break;
      case 'l':
        if (pidof)
          usage();
        list_signals();
        return 0;
        break;
      case 'q':
        if (pidof)
          usage();
        quiet = 1;
        break;
      case 'r':
	if (pidof)
	  usage();
	reg = 1;
	break;
      case 's':
	sig_num = get_signal (optarg, "killall");
        break;
      case 'u':
	if (pidof)
	  usage();
        if (!(pwent = getpwnam(optarg)))
	  {
            fprintf (stderr, _("Cannot find user %s\n"), optarg);
            exit (1);
          }
        break;
      case 'v':
        if (pidof)
          usage();
        verbose = 1;
        break;
      case 'w':
        if (pidof)
          usage();
        wait_until_dead = 1;
        break;
      case 'I':
        ignore_case = 1;
        break;
      case 'V':
        print_version();
        return 0;
        break;
#ifdef WITH_SELINUX
      case 'Z': 
        if (is_selinux_enabled()>0) {
	  scontext=optarg;
          if (regcomp(&scontext_reg, scontext, REG_EXTENDED|REG_NOSUB) != 0) {
            fprintf(stderr, _("Bad regular expression: %s\n"), scontext);
            exit (1);
	  }
        } else 
           fprintf(stderr, "Warning: -Z (--context) ignored. Requires an SELinux enabled kernel\n");
        break;
#endif /*WITH_SELINUX*/
      case '?':
        /* Signal names are in uppercase, so check to see if the argv
         * is upper case */
        if (argv[optind-1][1] >= 'A' && argv[optind-1][1] <= 'Z') {
	      sig_num = get_signal (argv[optind-1]+1, "killall");
        } else {
          /* Might also be a -## signal too */
          if (argv[optind-1][1] >= '0' && argv[optind-1][1] <= '9') {
            sig_num = atoi(argv[optind-1]+1);
          } else {
            usage();
          }
        }
        break;
    }
  }
  myoptind = optind;
#ifdef WITH_SELINUX
  if ((argc - myoptind < 1) && pwent==NULL && scontext==NULL) 
#else
  if ((argc - myoptind < 1) && pwent==NULL)	  
#endif
    usage();

  if (argc - myoptind > MAX_NAMES + 1)
    {
      fprintf (stderr, _("Maximum number of names is %d\n"), MAX_NAMES);
      exit (1);
    }
  if (stat("/proc/self/stat", &isproc)==-1)
    {
      fprintf (stderr, _("%s is empty (not mounted ?)\n"), PROC_BASE);
      exit (1);
    }
  argv = argv + myoptind;
  /*printf("sending signal %d to procs\n", sig_num);*/
#ifdef WITH_SELINUX
  return kill_all(sig_num,argc - myoptind, argv, pwent, 
		  		scontext ? &scontext_reg : NULL);
#else  /*WITH_SELINUX*/
  return kill_all(sig_num,argc - myoptind, argv, pwent);
#endif /*WITH_SELINUX*/
}