Exemple #1
0
/*
 * The trap builtin.
 */
int
trapcmd(int argc __unused, char **argv)
{
	char *action;
	int signo;
	int errors = 0;
	int i;

	while ((i = nextopt("l")) != '\0') {
		switch (i) {
		case 'l':
			printsignals();
			return (0);
		}
	}
	argv = argptr;

	if (*argv == NULL) {
		for (signo = 0 ; signo < sys_nsig ; signo++) {
			if (signo < NSIG && trap[signo] != NULL) {
				out1str("trap -- ");
				out1qstr(trap[signo]);
				if (signo == 0) {
					out1str(" EXIT\n");
				} else if (sys_signame[signo]) {
					out1fmt(" %s\n", sys_signame[signo]);
				} else {
					out1fmt(" %d\n", signo);
				}
			}
		}
		return 0;
	}
	action = NULL;
	if (*argv && sigstring_to_signum(*argv) == -1) {
		if (strcmp(*argv, "-") == 0)
			argv++;
		else {
			action = *argv;
			argv++;
		}
	}
	for (; *argv; argv++) {
		if ((signo = sigstring_to_signum(*argv)) == -1) {
			warning("bad signal %s", *argv);
			errors = 1;
			continue;
		}
		INTOFF;
		if (action)
			action = savestr(action);
		if (trap[signo])
			ckfree(trap[signo]);
		trap[signo] = action;
		if (signo != 0)
			setsignal(signo);
		INTON;
	}
	return errors;
}
Exemple #2
0
int
exportcmd(shinstance *psh, int argc, char **argv)
{
    struct var *vp;
    char *name;
    const char *p;
    int flag = argv[0][0] == 'r'? VREADONLY : VEXPORT;
    int pflag;

    pflag = nextopt(psh, "p") == 'p' ? 3 : 0;
    if (argc <= 1 || pflag) {
        showvars(psh, pflag ? argv[0] : 0, flag, pflag );
        return 0;
    }

    while ((name = *psh->argptr++) != NULL) {
        if ((p = strchr(name, '=')) != NULL) {
            p++;
        } else {
            vp = find_var(psh, name, NULL, NULL);
            if (vp != NULL) {
                vp->flags |= flag;
                continue;
            }
        }
        setvar(psh, name, p, flag);
    }
    return 0;
}
Exemple #3
0
int
fgcmd(int argc, char **argv)
{
	struct job *jp;
	int i;
	int status;

	nextopt("");
	jp = getjob(*argptr, 0);
	if (jp->jobctl == 0)
		error("job not created under job control");
	out1fmt("%s", jp->ps[0].cmd);
	for (i = 1; i < jp->nprocs; i++)
		out1fmt(" | %s", jp->ps[i].cmd );
	out1c('\n');
	flushall();

	for (i = 0; i < jp->nprocs; i++)
	    if (tcsetpgrp(ttyfd, jp->ps[i].pid) != -1)
		    break;

	if (i >= jp->nprocs) {
		error("Cannot set tty process group (%s) at %d",
		    strerror(errno), __LINE__);
	}
	restartjob(jp);
	INTOFF;
	status = waitforjob(jp);
	INTON;
	return status;
}
Exemple #4
0
int
unsetcmd(shinstance *psh, int argc, char **argv)
{
    char **ap;
    int i;
    int flg_func = 0;
    int flg_var = 0;
    int ret = 0;

    while ((i = nextopt(psh, "evf")) != '\0') {
        if (i == 'f')
            flg_func = 1;
        else
            flg_var = i;
    }
    if (flg_func == 0 && flg_var == 0)
        flg_var = 1;

    for (ap = psh->argptr; *ap ; ap++) {
        if (flg_func)
            ret |= unsetfunc(psh, *ap);
        if (flg_var)
            ret |= unsetvar(psh, *ap, flg_var == 'e');
    }
    return ret;
}
Exemple #5
0
int
readcmd(int argc, char **argv)
{
	char **ap;
	int backslash;
	char c;
	int rflag;
	char *prompt;
	char *p;
	int status;
	int i;

	rflag = 0;
	prompt = NULL;
	while ((i = nextopt("p:r")) != '\0') {
		if (i == 'p')
			prompt = optionarg;
		else
			rflag = 1;
	}
	if (prompt && isatty(0)) {
		out2str(prompt);
#ifdef FLUSHERR
		flushall();
#endif
	}
	if (*(ap = argptr) == NULL)
		sh_error("arg count");
	status = 0;
	backslash = 0;
	STARTSTACKSTR(p);
	for (;;) {
		if (read(0, &c, 1) != 1) {
			status = 1;
			break;
		}
		if (c == '\0')
			continue;
		if (backslash) {
			if (c == '\n')
				goto resetbs;
			STPUTC(CTLESC, p);
			goto put;
		}
		if (!rflag && c == '\\') {
			backslash++;
			continue;
		}
		if (c == '\n')
			break;
put:
		STPUTC(c, p);
resetbs:
		backslash = 0;
	}
	STACKSTRNUL(p);
	readcmd_handle_line(stackblock(), ap, p + 1 - (char *)stackblock());
	return status;
}
Exemple #6
0
int
waitcmd(int argc, char **argv)
{
	struct job *job;
	int status, retval;
	struct job *jp;

	nextopt("");

	if (!*argptr) {
		/* wait for all jobs */
		jp = jobtab;
		if (jobs_invalid)
			return 0;
		for (;;) {
			if (jp >= jobtab + njobs) {
				/* no running procs */
				return 0;
			}
			if (!jp->used || jp->state != JOBRUNNING) {
				jp++;
				continue;
			}
			if (dowait(WBLOCK, NULL) == -1)
			       return 128 + SIGINT;
			jp = jobtab;
		}
	}

	retval = 127;		/* XXXGCC: -Wuninitialized */
	for (; *argptr; argptr++) {
		job = getjob(*argptr, 1);
		if (!job) {
			retval = 127;
			continue;
		}
		/* loop until process terminated or stopped */
		while (job->state == JOBRUNNING) {
			if (dowait(WBLOCK|WNOFREE, job) == -1)
			       return 128 + SIGINT;
		}
		status = job->ps[job->nprocs ? job->nprocs - 1 : 0].status;
		if (WIFEXITED(status))
			retval = WEXITSTATUS(status);
#if JOBS
		else if (WIFSTOPPED(status))
			retval = WSTOPSIG(status) + 128;
#endif
		else {
			/* XXX: limits number of signals */
			retval = WTERMSIG(status) + 128;
		}
		if (!iflag)
			freejob(job);
	}
	return retval;
}
Exemple #7
0
int
main(int argc, char *argv[])
{
	const char *modestr = NULL;
	const void *modep;
	mode_t fifomode;
	int ch, exitval;

#ifdef SHELL
	while ((ch = nextopt("m:")) != '\0')
#else
	while ((ch = getopt(argc, argv, "m:")) != -1)
#endif
		switch(ch) {
		case 'm':
			f_mode = 1;
#ifdef shell
			modestr = shoptarg;
#else
			modestr = optarg;
#endif
			break;
		case '?':
		default:
			usage();
		}
#ifdef SHELL
	argc -= argptr - argv;
	argv = argptr;
#else
	argc -= optind;
	argv += optind;
#endif
	if (argv[0] == NULL)
		usage();

	if (f_mode) {
		umask(0);
		errno = 0;
		if ((modep = setmode(modestr)) == NULL) {
			if (errno)
				err(1, "%s", "setmode");
			errx(1, "invalid file mode: %s", modestr);
		}
		fifomode = getmode(modep, BASEMODE);
	} else {
		fifomode = BASEMODE;
	}

	for (exitval = 0; *argv != NULL; ++argv)
		if (mkfifo(*argv, fifomode) < 0) {
			warn("%s", *argv);
			exitval = 1;
		}
	return(exitval);
}
Exemple #8
0
int
trapcmd(int argc, char **argv)
{
    char *action;
    char **ap;
    int signo;

    nextopt(nullstr);
    ap = argptr;
    if (!*ap) {
        for (signo = 0 ; signo < NSIG ; signo++) {
            if (trap[signo] != NULL) {
                out1fmt(
                    "trap -- %s %s\n",
                    single_quote(trap[signo]),
                    signal_names[signo]
                );
            }
        }
        return 0;
    }
    if (!ap[1])
        action = NULL;
    else
        action = *ap++;
    while (*ap) {
        if ((signo = decode_signal(*ap, 0)) < 0) {
            outfmt(out2, "trap: %s: bad trap\n", *ap);
            return 1;
        }
        INTOFF;
        if (action) {
            if (action[0] == '-' && action[1] == '\0')
                action = NULL;
            else {
                if (*action)
                    trapcnt++;
                action = savestr(action);
            }
        }
        if (trap[signo]) {
            if (*trap[signo])
                trapcnt--;
            ckfree(trap[signo]);
        }
        trap[signo] = action;
        if (signo != 0)
            setsignal(signo);
        INTON;
        ap++;
    }
    return 0;
}
Exemple #9
0
int
main(int argc, char *argv[], char *envp[])
{
  nextopt_t  nopt = nextopt_INIT(argc, argv, "hV");
  char       opt;
  pid_t      pid;

  progname = nextopt_progname(&nopt);
  while((opt = nextopt(&nopt))){
      char optc[2] = {nopt.opt_got, '\0'};
      switch(opt){
      case 'h': usage(); die(0); break;
      case 'V': version(); die(0); break;
      case ':':
          fatal_usage("missing argument for option -", optc);
          break;
      case '?':
          if(nopt.opt_got != '?'){
              fatal_usage("invalid option: -", optc);
          }
          /* else fallthrough: */
      default :
          die_usage(); break; 
      }
  }

  argc -= nopt.arg_ndx;
  argv += nopt.arg_ndx;

  if(argc < 1){
      fatal_usage("missing required program argument");
  }

  if((pid = fork()) == -1){
      fatal_syserr("failure to detach");
  }
  if(pid != 0){
      /* parent exits: */
      _exit(0);
  }
  setsid(); 

  /* execvx() provides path search for prog */
  execvx(argv[0], argv, envp, NULL);

  /* uh oh: */
  fatal_syserr("unable to run ", argv[0]);

  /* not reached: */
  return 0;
}
Exemple #10
0
int
jobidcmd(int argc, char **argv)
{
	struct job *jp;
	int i;

	nextopt("");
	jp = getjob(*argptr, 0);
	for (i = 0 ; i < jp->nprocs ; ) {
		out1fmt("%ld", (long)jp->ps[i].pid);
		out1c(++i < jp->nprocs ? ' ' : '\n');
	}
	return 0;
}
Exemple #11
0
int
main(int argc, char *argv[], char *envp[])
{
  nextopt_t    nopt = nextopt_INIT(argc, argv, "hV");
  char         opt;
  const char  *prog = NULL;

  progname = nextopt_progname(&nopt);
  while((opt = nextopt(&nopt))){
      char optc[2] = {nopt.opt_got, '\0'};
      switch(opt){
      case 'h': usage(); die(0); break;
      case 'V': version(); die(0); break;
      case ':':
          fatal_usage("missing argument for option -", optc);
          break;
      case '?':
          if(nopt.opt_got != '?'){
              fatal_usage("invalid option: -", optc);
          }
          /* else fallthrough: */
      default :
          die_usage(); break; 
      }
  }

  argc -= nopt.arg_ndx;
  argv += nopt.arg_ndx;

  if(argc < 2){
      fatal_usage("missing required argument(s)");
  }

  /* our real executable: */
  prog = argv[0];

  /* ratchet alias into argv[0]: */
  ++argv;

  /* execvx() provides path search for prog */
  execvx(prog, argv, envp, NULL);

  /* uh oh: */
  fatal_syserr("unable to run ", prog);

  /* not reached: */
  return 0;
}
Exemple #12
0
int
unaliascmd(int argc, char **argv)
{
	int i;

	while ((i = nextopt("a")) != '\0') {
		if (i == 'a') {
			rmaliases();
			return (0);
		}
	}
	for (i = 0; *argptr; argptr++)
		i = unalias(*argptr);

	return (i);
}
Exemple #13
0
int
main(int argc, char *argv[])
{
  nextopt_t  nopt = nextopt_INIT(argc, argv, "hV");
  char       opt;
  int        i;

  progname = nextopt_progname(&nopt);
  while((opt = nextopt(&nopt))){
      char optc[2] = {nopt.opt_got, '\0'};
      switch(opt){
      case 'V': version(); die(0); break;
      case 'h': usage(); die(0); break;
      case '?':
          if(nopt.opt_got != '?'){
              eputs(progname, ": usage error: invalid option: -", optc);
          }
          /* fallthrough: */
      default :
          die_usage(); break; 
      }
  }

  argc -= nopt.arg_ndx;
  argv += nopt.arg_ndx;

  for(i = 0; resources[i] != NULL; ++i){
      const char  *resource = resources[i];
      int  r = rlimit_lookup(resource);
      char  nfmt[NFMT_SIZE];
      struct rlimit  rlim;
      if(r == -1){
          ioq_vputs(ioq1, resource, "\t[not provided on this platform]\n");
          continue;
      }
      getrlimit(r, &rlim);
      ioq_vputs(ioq1, resource, "\t", rlimit_mesg(r), ": "); 
      if(rlim.rlim_cur == RLIM_INFINITY){
          ioq_vputs(ioq1, "unlimited\n");
      } else {
          ioq_vputs(ioq1, nfmt_uint32(nfmt, rlim.rlim_cur), "\n");
      }
  }
  ioq_flush(ioq1);

  return 0;
}
Exemple #14
0
int
dotcmd(int argc, char **argv)
{
	int status = 0;

	nextopt(nullstr);
	argv = argptr;

	if (*argv) {
		char *fullname;

		fullname = find_dot_file(*argv);
		setinputfile(fullname, INPUT_PUSH_FILE);
		commandname = fullname;
		status = cmdloop(0);
		popfile();
	}

	return status;
}
Exemple #15
0
int
unaliascmd(int argc, char **argv)
{
	int i;

	while ((i = nextopt("a")) != '\0') {
		if (i == 'a') {
			rmaliases();
			return (0);
		}
	}
	for (i = 0; *argptr; argptr++) {
		if (unalias(*argptr)) {
			outfmt(out2, "%s: %s not found\n", "unalias", *argptr);
			i = 1;
		}
	}

	return (i);
}
Exemple #16
0
int
timescmd(int argc, char **argv)
{
	struct tms tms;
	int u, s, cu, cs;
	char us[8], ss[8], cus[8], css[8];

	nextopt("");

	times(&tms);

	u = conv_time(tms.tms_utime, us, sizeof(us));
	s = conv_time(tms.tms_stime, ss, sizeof(ss));
	cu = conv_time(tms.tms_cutime, cus, sizeof(cus));
	cs = conv_time(tms.tms_cstime, css, sizeof(css));

	outfmt(out1, "%dm%ss %dm%ss\n%dm%ss %dm%ss\n",
		u, us, s, ss, cu, cus, cs, css);

	return 0;
}
Exemple #17
0
int
bgcmd(int argc, char **argv)
{
	struct job *jp;
	int i;

	nextopt("");
	do {
		jp = getjob(*argptr, 0);
		if (jp->jobctl == 0)
			error("job not created under job control");
		set_curjob(jp, 1);
		out1fmt("[%ld] %s", (long)(jp - jobtab + 1), jp->ps[0].cmd);
		for (i = 1; i < jp->nprocs; i++)
			out1fmt(" | %s", jp->ps[i].cmd );
		out1c('\n');
		flushall();
		restartjob(jp);
	} while (*argptr && *++argptr);
	return 0;
}
Exemple #18
0
int
timescmd(shinstance *psh, int argc, char **argv)
{
	shtms tms;
	int u, s, cu, cs;
	char us[8], ss[8], cus[8], css[8];

	nextopt(psh, "");

	sh_times(psh, &tms);

	u = conv_time(tms.tms_utime, us, sizeof(us));
	s = conv_time(tms.tms_stime, ss, sizeof(ss));
	cu = conv_time(tms.tms_cutime, cus, sizeof(cus));
	cs = conv_time(tms.tms_cstime, css, sizeof(css));

	outfmt(psh->out1, "%dm%ss %dm%ss\n%dm%ss %dm%ss\n",
		u, us, s, ss, cu, cus, cs, css);

	return 0;
}
Exemple #19
0
int
jobscmd(int argc, char **argv)
{
	int mode, m;
	int sv = jobs_invalid;

	jobs_invalid = 0;
	mode = 0;
	while ((m = nextopt("lp")))
		if (m == 'l')
			mode = SHOW_PID;
		else
			mode = SHOW_PGID;
	if (*argptr)
		do
			showjob(out1, getjob(*argptr,0), mode);
		while (*++argptr);
	else
		showjobs(out1, mode);
	jobs_invalid = sv;
	return 0;
}
Exemple #20
0
int
main(int argc, char *argv[])
{
  nextopt_t  nopt = nextopt_INIT(argc, argv, ":hVdL:S:x");
  char       opt;
  int        opt_detach = 0;
  char      *arg_sep = "::";

  progname = nextopt_progname(&nopt);
  while((opt = nextopt(&nopt))){
      char optc[2] = {nopt.opt_got, '\0'};
      switch(opt){
      case 'h': usage(); die(0); break;
      case 'V': version(); die(0); break;
      case 'd': opt_detach = 1; break;
      case 'L': /* label string ignored */ break;
      case 'S': arg_sep = nopt.opt_arg; break;
      case 'x': opt_super = 0; break;
      case ':':
          fatal_usage("missing argument for option -", optc);
          break;
      case '?':
          if(nopt.opt_got != '?'){
              fatal_usage("invalid option: -", optc);
          }
          /* else fallthrough: */
      default :
          die_usage(); break; 
      }
  }

  argc -= nopt.arg_ndx;
  argv += nopt.arg_ndx;

  if(argc < 3){
      fatal_usage("missing required arguments");
  }

  deux_init();

  /* proggy: */
  deux[1].argv = argv;
  ++argv;
  while(argv){
      if(cstr_cmp(*argv, arg_sep) == 0){
          /* logger argv follows separator: */
          deux[0].argv = &argv[1];
          /* progger argv terminator: */
          *argv = NULL;
          break;
      }
      ++argv;
  }
  if(deux[0].argv == NULL){
      fatal_usage("missing required logger argument");
  }

  if(opt_detach){
      pid_t  pid = fork();
      switch(pid){
      case -1: fatal_syserr("unable to detach"); break;
      case 0:
          /* child continues daemonized in new session: */
          setsid(); break;
      default:
          /* parent exits: */
          exit(0);
      }
  }

  /* initialize sigpipe[], etc: */
  setup();
  main_loop();

  return 0;
}
int
ulimitcmd(int argc, char **argv)
{
	int	c;
	rlim_t val = 0;
	enum { SOFT = 0x1, HARD = 0x2 }
			how = SOFT | HARD;
	const struct limits	*l;
	int		set, all = 0;
	int		optc, what;
	struct rlimit	limit;

	what = 'f';
	while ((optc = nextopt("HSabtfdsmcnpl")) != '\0')
		switch (optc) {
		case 'H':
			how = HARD;
			break;
		case 'S':
			how = SOFT;
			break;
		case 'a':
			all = 1;
			break;
		default:
			what = optc;
		}

	for (l = limits; l->name && l->option != what; l++)
		;
	if (!l->name)
		error("internal error (%c)", what);

	set = *argptr ? 1 : 0;
	if (set) {
		char *p = *argptr;

		if (all || argptr[1])
			error("too many arguments");
		if (strcmp(p, "unlimited") == 0)
			val = RLIM_INFINITY;
		else {
			val = (rlim_t) 0;

			while ((c = *p++) >= '0' && c <= '9')
			{
				val = (val * 10) + (long)(c - '0');
				if ((long)val < 0)
					break;
			}
			if (c)
				error("bad number");
			val *= l->factor;
		}
	}
	if (all) {
		for (l = limits; l->name; l++) {
			getrlimit(l->cmd, &limit);
			if (how & SOFT)
				val = limit.rlim_cur;
			else if (how & HARD)
				val = limit.rlim_max;

			out1fmt("%-20s ", l->name);
			if (val == RLIM_INFINITY)
				out1fmt("unlimited\n");
			else
			{
				val /= l->factor;
#ifdef BSD4_4
				out1fmt("%lld\n", (long long) val);
#else
				out1fmt("%ld\n", (long) val);
#endif
			}
		}
		return 0;
	}

	getrlimit(l->cmd, &limit);
	if (set) {
		if (how & HARD)
			limit.rlim_max = val;
		if (how & SOFT)
			limit.rlim_cur = val;
		if (setrlimit(l->cmd, &limit) < 0)
			error("error setting limit (%s)", strerror(errno));
	} else {
		if (how & SOFT)
			val = limit.rlim_cur;
		else if (how & HARD)
			val = limit.rlim_max;

		if (val == RLIM_INFINITY)
			out1fmt("unlimited\n");
		else
		{
			val /= l->factor;
#ifdef BSD4_4
			out1fmt("%lld\n", (long long) val);
#else
			out1fmt("%ld\n", (long) val);
#endif
		}
	}
	return 0;
}
int
readcmd(int argc, char **argv)
{
	char **ap;
	char c;
	int rflag;
	char *prompt;
	const char *ifs;
	char *p;
	int startword;
	int status;
	int i;
	int is_ifs;
	int saveall = 0;

	rflag = 0;
	prompt = NULL;
	while ((i = nextopt("p:r")) != '\0') {
		if (i == 'p')
			prompt = optionarg;
		else
			rflag = 1;
	}

	if (prompt && isatty(0)) {
		out2str(prompt);
		flushall();
	}

	if (*(ap = argptr) == NULL)
		error("arg count");

	if ((ifs = bltinlookup("IFS", 1)) == NULL)
		ifs = " \t\n";

	status = 0;
	startword = 2;
	STARTSTACKSTR(p);
	for (;;) {
		if (read(0, &c, 1) != 1) {
			status = 1;
			break;
		}
		if (c == '\0')
			continue;
		if (c == '\\' && !rflag) {
			if (read(0, &c, 1) != 1) {
				status = 1;
				break;
			}
			if (c != '\n')
				STPUTC(c, p);
			continue;
		}
		if (c == '\n')
			break;
		if (strchr(ifs, c))
			is_ifs = strchr(" \t\n", c) ? 1 : 2;
		else
			is_ifs = 0;

		if (startword != 0) {
			if (is_ifs == 1) {
				/* Ignore leading IFS whitespace */
				if (saveall)
					STPUTC(c, p);
				continue;
			}
			if (is_ifs == 2 && startword == 1) {
				/* Only one non-whitespace IFS per word */
				startword = 2;
				if (saveall)
					STPUTC(c, p);
				continue;
			}
		}

		if (is_ifs == 0) {
			/* append this character to the current variable */
			startword = 0;
			if (saveall)
				/* Not just a spare terminator */
				saveall++;
			STPUTC(c, p);
			continue;
		}

		/* end of variable... */
		startword = is_ifs;

		if (ap[1] == NULL) {
			/* Last variable needs all IFS chars */
			saveall++;
			STPUTC(c, p);
			continue;
		}

		STACKSTRNUL(p);
		setvar(*ap, stackblock(), 0);
		ap++;
		STARTSTACKSTR(p);
	}
	STACKSTRNUL(p);

	/* Remove trailing IFS chars */
	for (; stackblock() <= --p; *p = 0) {
		if (!strchr(ifs, *p))
			break;
		if (strchr(" \t\n", *p))
			/* Always remove whitespace */
			continue;
		if (saveall > 1)
			/* Don't remove non-whitespace unless it was naked */
			break;
	}
	setvar(*ap, stackblock(), 0);

	/* Set any remaining args to "" */
	while (*++ap != NULL)
		setvar(*ap, nullstr, 0);
	return status;
}
Exemple #23
0
int
ulimitcmd(int argc, char **argv)
{
	int	c;
	rlim_t val = 0;
	enum limtype how = SOFT | HARD;
	const struct limits	*l;
	int		set, all = 0;
	int		optc, what;
	struct rlimit	limit;

	what = 'f';
	while ((optc = nextopt("HSa"
#ifdef RLIMIT_CPU
			       "t"
#endif
#ifdef RLIMIT_FSIZE
			       "f"
#endif
#ifdef RLIMIT_DATA
			       "d"
#endif
#ifdef RLIMIT_STACK
			       "s"
#endif
#ifdef RLIMIT_CORE
			       "c"
#endif
#ifdef RLIMIT_RSS
			       "m"
#endif
#ifdef RLIMIT_MEMLOCK
			       "l"
#endif
#ifdef RLIMIT_NPROC
			       "p"
#endif
#ifdef RLIMIT_NOFILE
			       "n"
#endif
#ifdef RLIMIT_AS
			       "v"
#endif
#ifdef RLIMIT_LOCKS
			       "w"
#endif
	)) != '\0')
		switch (optc) {
		case 'H':
			how = HARD;
			break;
		case 'S':
			how = SOFT;
			break;
		case 'a':
			all = 1;
			break;
		default:
			what = optc;
		}

	for (l = limits; l->option != what; l++)
		;

	set = *argptr ? 1 : 0;
	if (set) {
		char *p = *argptr;

		if (all || argptr[1])
			sh_error("too many arguments");
		if (strcmp(p, "unlimited") == 0)
			val = RLIM_INFINITY;
		else {
			val = (rlim_t) 0;

			while ((c = *p++) >= '0' && c <= '9')
			{
				val = (val * 10) + (long)(c - '0');
				if (val < (rlim_t) 0)
					break;
			}
			if (c)
				sh_error("bad number");
			val *= l->factor;
		}
	}
	if (all) {
		for (l = limits; l->name; l++) {
			getrlimit(l->cmd, &limit);
			out1fmt("%-20s ", l->name);
			printlim(how, &limit, l);
		}
		return 0;
	}

	getrlimit(l->cmd, &limit);
	if (set) {
		if (how & HARD)
			limit.rlim_max = val;
		if (how & SOFT)
			limit.rlim_cur = val;
		if (setrlimit(l->cmd, &limit) < 0)
			sh_error("error setting limit (%s)", strerror(errno));
	} else {
		printlim(how, &limit, l);
	}
	return 0;
}
Exemple #24
0
int
umaskcmd(int argc, char **argv)
{
	char *ap;
	int mask;
	int i;
	int symbolic_mode = 0;

	while ((i = nextopt("S")) != '\0') {
		symbolic_mode = 1;
	}

	INTOFF;
	mask = umask(0);
	umask(mask);
	INTON;

	if ((ap = *argptr) == NULL) {
		if (symbolic_mode) {
			char buf[18];
			int j;

			mask = ~mask;
			ap = buf;
			for (i = 0; i < 3; i++) {
				*ap++ = "ugo"[i];
				*ap++ = '=';
				for (j = 0; j < 3; j++)
					if (mask & (1 << (8 - (3*i + j))))
						*ap++ = "rwx"[j];
				*ap++ = ',';
			}
			ap[-1] = '\0';
			out1fmt("%s\n", buf);
		} else {
			out1fmt("%.4o\n", mask);
		}
	} else {
		int new_mask;

		if (isdigit((unsigned char) *ap)) {
			new_mask = 0;
			do {
				if (*ap >= '8' || *ap < '0')
					sh_error(illnum, *argptr);
				new_mask = (new_mask << 3) + (*ap - '0');
			} while (*++ap != '\0');
		} else {
			int positions, new_val;
			char op;

			mask = ~mask;
			new_mask = mask;
			positions = 0;
			while (*ap) {
				while (*ap && strchr("augo", *ap))
					switch (*ap++) {
					case 'a': positions |= 0111; break;
					case 'u': positions |= 0100; break;
					case 'g': positions |= 0010; break;
					case 'o': positions |= 0001; break;
					}
				if (!positions)
					positions = 0111; /* default is a */
				if (!strchr("=+-", op = *ap))
					break;
				ap++;
				new_val = 0;
				while (*ap && strchr("rwxugoXs", *ap))
					switch (*ap++) {
					case 'r': new_val |= 04; break;
					case 'w': new_val |= 02; break;
					case 'x': new_val |= 01; break;
					case 'u': new_val |= mask >> 6;
						  break;
					case 'g': new_val |= mask >> 3;
						  break;
					case 'o': new_val |= mask >> 0;
						  break;
					case 'X': if (mask & 0111)
							new_val |= 01;
						  break;
					case 's': /* ignored */
						  break;
					}
				new_val = (new_val & 07) * positions;
				switch (op) {
				case '-':
					new_mask &= ~new_val;
					break;
				case '=':
					new_mask = new_val
					    | (new_mask & ~(positions * 07));
					break;
				case '+':
					new_mask |= new_val;
				}
				if (*ap == ',') {
					positions = 0;
					ap++;
				} else if (!strchr("=+-", *ap))
					break;
			}
			if (*ap) {
				sh_error("Illegal mode: %s", *argptr);
				return 1;
			}
			new_mask = ~new_mask;
		}
		umask(new_mask);
	}
	return 0;
}
Exemple #25
0
int
readcmd(int argc, char **argv)
{
	char **ap;
	char c;
	int rflag;
	char *prompt;
	char *p;
	int startloc;
	int newloc;
	int status;
	int i;

	rflag = 0;
	prompt = NULL;
	while ((i = nextopt("p:r")) != '\0') {
		if (i == 'p')
			prompt = optionarg;
		else
			rflag = 1;
	}
	if (prompt && isatty(0)) {
		out2str(prompt);
#ifdef FLUSHERR
		flushall();
#endif
	}
	if (*(ap = argptr) == NULL)
		sh_error("arg count");

	status = 0;
	STARTSTACKSTR(p);

	goto start;

	for (;;) {
		switch (read(0, &c, 1)) {
		case 1:
			break;
		default:
			if (errno == EINTR && !pendingsigs)
				continue;
				/* fall through */
		case 0:
			status = 1;
			goto out;
		}
		if (c == '\0')
			continue;
		if (newloc >= startloc) {
			if (c == '\n')
				goto resetbs;
			goto put;
		}
		if (!rflag && c == '\\') {
			newloc = p - (char *)stackblock();
			continue;
		}
		if (c == '\n')
			break;
put:
		CHECKSTRSPACE(2, p);
		if (strchr(qchars, c))
			USTPUTC(CTLESC, p);
		USTPUTC(c, p);

		if (newloc >= startloc) {
resetbs:
			recordregion(startloc, newloc, 0);
start:
			startloc = p - (char *)stackblock();
			newloc = startloc - 1;
		}
	}
out:
	recordregion(startloc, p - (char *)stackblock(), 0);
	STACKSTRNUL(p);
	readcmd_handle_line(p + 1, ap);
	return status;
}
Exemple #26
0
int32_t
printfcmd(int32_t argc, cstring_t argv[])
{
	size_t len;
	int32_t chopped, end, rval;
	cstring_t format;
	cstring_t fmt;
	cstring_t start;
	nextopt("");
	argc -= (int32_t)(intptr_t)(argptr - argv);
	argv = argptr;
	if (argc < 1)
	{
		usage();
		return (1);
	}
	INTOFF;
	/*
	 * Basic algorithm is to scan the format string for conversion
	 * specifications -- once one is found, find out if the field
	 * width or precision is a '*'; if it is, gather up value.  Note,
	 * format strings are reused as necessary to use up the provided
	 * arguments, arguments of zero/null string are provided to use
	 * up the format string.
	 */
	fmt = format = *argv;
	chopped = escape(fmt, 1, &len);		/* backslash interpretation */
	rval = end = 0;
	gargv = ++argv;
	for (;;)
	{
		start = fmt;
		while (fmt < format + len)
		{
			if (fmt[0] == '%')
			{
				fwrite(start, 1, fmt - start, stdout);
				if (fmt[1] == '%')
				{
					/* %% prints a % */
					putchar('%');
					fmt += 2;
				}
				else
				{
					fmt = printf_doformat(fmt, &rval);
					if (fmt == NULL)
					{
						INTON;
						return (1);
					}
					end = 0;
				}
				start = fmt;
			}
			else
				fmt++;
		}
		if (end == 1)
		{
			warnx("missing format character");
			INTON;
			return (1);
		}
		fwrite(start, 1, fmt - start, stdout);
		if (chopped || !*gargv)
		{
			INTON;
			return (rval);
		}
		/* Restart at the beginning of the format string. */
		fmt = format;
		end = 1;
	}
	/* NOTREACHED */
}
Exemple #27
0
int printfcmd(int argc, char *argv[])
{
	char *fmt;
	char *format;
	int ch;

	rval = 0;

	nextopt(nullstr);

	argv = argptr;
	format = *argv;

	if (!format) {
		warnx("usage: printf format [arg ...]");
		goto err;
	}

	gargv = ++argv;

#define SKIP1	"#-+ 0"
#define SKIP2	"*0123456789"
	do {
		/*
		 * Basic algorithm is to scan the format string for conversion
		 * specifications -- once one is found, find out if the field
		 * width or precision is a '*'; if it is, gather up value. 
		 * Note, format strings are reused as necessary to use up the
		 * provided arguments, arguments of zero/null string are 
		 * provided to use up the format string.
		 */

		/* find next format specification */
		for (fmt = format; (ch = *fmt++) ;) {
			char *start;
			char nextch;
			int array[2];
			int *param;

			if (ch == '\\') {
				int c_ch;
				fmt = conv_escape(fmt, &c_ch);
				ch = c_ch;
				goto pc;
			}
			if (ch != '%' || (*fmt == '%' && (++fmt || 1))) {
pc:
				blt_putchar(ch);
				continue;
			}

			/* Ok - we've found a format specification,
			   Save its address for a later blt_printf(). */
			start = fmt - 1;
			param = array;

			/* skip to field width */
			fmt += strspn(fmt, SKIP1);
			if (*fmt == '*')
				*param++ = getintmax();

			/* skip to possible '.', get following precision */
			fmt += strspn(fmt, SKIP2);
			if (*fmt == '.')
				++fmt;
			if (*fmt == '*')
				*param++ = getintmax();

			fmt += strspn(fmt, SKIP2);

			ch = *fmt;
			if (!ch) {
				warnx("missing format character");
				goto err;
			}
			/* null terminate format string to we can use it
			   as an argument to printf. */
			nextch = fmt[1];
			fmt[1] = 0;
			switch (ch) {

			case 'b': {
				int done = conv_escape_str(getstr());
				char *p = stackblock();
				*fmt = 's';
				PF(start, p);
				/* escape if a \c was encountered */
				if (done)
					goto out;
				*fmt = 'b';
				break;
			}
			case 'c': {
				int p = getchr();
				PF(start, p);
				break;
			}
			case 's': {
				char *p = getstr();
				PF(start, p);
				break;
			}
			case 'd':
			case 'i': {
				intmax_t p = getintmax();
				char *f = mklong(start, fmt);
				PF(f, p);
				break;
			}
			case 'o':
			case 'u':
			case 'x':
			case 'X': {
				uintmax_t p = getuintmax();
				char *f = mklong(start, fmt);
				PF(f, p);
				break;
			}
			case 'e':
			case 'E':
			case 'f':
			case 'g':
			case 'G': {
				double p = getdouble();
				PF(start, p);
				break;
			}
			default:
				warnx("%s: invalid directive", start);
				goto err;
			}
			*++fmt = nextch;
		}
	} while (gargv != argv && *gargv);

out:
	return rval;
err:
	return 1;
}
int
umaskcmd(int argc, char **argv)
{
	char *ap;
	int mask;
	int i;
	int symbolic_mode = 0;

	while ((i = nextopt("S")) != '\0') {
		symbolic_mode = 1;
	}

	INTOFF;
	mask = umask(0);
	umask(mask);
	INTON;

	if ((ap = *argptr) == NULL) {
		if (symbolic_mode) {
			char u[4], g[4], o[4];

			i = 0;
			if ((mask & S_IRUSR) == 0)
				u[i++] = 'r';
			if ((mask & S_IWUSR) == 0)
				u[i++] = 'w';
			if ((mask & S_IXUSR) == 0)
				u[i++] = 'x';
			u[i] = '\0';

			i = 0;
			if ((mask & S_IRGRP) == 0)
				g[i++] = 'r';
			if ((mask & S_IWGRP) == 0)
				g[i++] = 'w';
			if ((mask & S_IXGRP) == 0)
				g[i++] = 'x';
			g[i] = '\0';

			i = 0;
			if ((mask & S_IROTH) == 0)
				o[i++] = 'r';
			if ((mask & S_IWOTH) == 0)
				o[i++] = 'w';
			if ((mask & S_IXOTH) == 0)
				o[i++] = 'x';
			o[i] = '\0';

			out1fmt("u=%s,g=%s,o=%s\n", u, g, o);
		} else {
			out1fmt("%.4o\n", mask);
		}
	} else {
		if (isdigit((unsigned char)*ap)) {
			mask = 0;
			do {
				if (*ap >= '8' || *ap < '0')
					error("Illegal number: %s", argv[1]);
				mask = (mask << 3) + (*ap - '0');
			} while (*++ap != '\0');
			umask(mask);
		} else
			error("Illegal mode: %s", ap);
	}
	return 0;
}
Exemple #29
0
int
main(int argc, char *argv[], char *envp[])
{
  nextopt_t    nopt = nextopt_INIT(argc, argv, ":hVb:ek:p:s:v");
  char         opt;
  const char  *prog = NULL;
  uint32_t     pid = 0;
  const char  *z;
  size_t       n;
 
  progname = nextopt_progname(&nopt);
  while((opt = nextopt(&nopt))){
      char optc[2] = {nopt.opt_got, '\0'};
      switch(opt){
      case 'V': version(); die(0); break;
      case 'h': usage(); die(0); break;
      case 'b': arg_base = nopt.opt_arg; break;
      case 'e': ++opt_e; break;
      case 'k': arg_key = nopt.opt_arg; break;
      case 'p':
          z = nuscan_uint32(&pid, nopt.opt_arg);
          if(*z != '\0'){
              fatal_usage("bad numeric argument for -", optc, ": ", nopt.opt_arg);
          }
          break;
      case 's': arg_set = nopt.opt_arg; break;
      case 'v': ++opt_v; break;
      case ':':
          fatal_usage("missing argument for option -", optc);
          break;
      case '?':
          if(nopt.opt_got != '?'){
              fatal_usage("invalid option: -", optc);
          }
          /* else fallthrough: */
      default :
          die_usage(); break; 
      }
  }

  argc -= nopt.arg_ndx;
  argv += nopt.arg_ndx;

  if(argc > 0) prog = argv[0];
  if(prog == NULL){
      fatal_usage("missing required program argument");
  }

  if(arg_base == NULL)
      arg_base = getenv("CHOOM_BASE");
  if(arg_base == NULL)
      arg_base = CHOOM_BASE_DEFAULT;

  if(arg_base[0] != '/'){
      fatal_usage("path base is not absolute (must begin with `/'): ", arg_base);
  }

  if(arg_key == NULL)
      arg_key = getenv("CHOOM_KEY");
  if(arg_key == NULL)
      arg_key = CHOOM_KEY_DEFAULT;

  if(arg_set == NULL)
      arg_set = getenv("CHOOM_SET");
  if(arg_set == NULL)
      arg_set = CHOOM_SET_DEFAULT;

  nfmt_uint32(pidfmt, (pid == 0) ? (uint32_t)getpid() : pid); 

  n = cstr_vlen(arg_base, "/", pidfmt, "/", arg_key);
  if((sizeof pathbuf) - n < 5){
      errno = ENAMETOOLONG;
      fatal_syserr("path too long: ", arg_base, "/", pidfmt, "/", arg_key);
  }
  cstr_vcopy(pathbuf, arg_base, "/", pidfmt, "/", arg_key);

  n = cstr_vlen(arg_set, "\n");
  if((sizeof setbuf) - n < 1){
      fatal_usage("setting too long: ", arg_set);
  }
  cstr_vcopy(setbuf, arg_set, "\n");

  do_choom();

  execvx(prog, argv, envp, NULL);
  fatal_syserr("unable to run ", prog); 

  /* not reached: */
  return 0;
}
Exemple #30
0
int
main(int argc, char *argv[], char *envp[])
{
  nextopt_t    nopt = nextopt_INIT(argc, argv, ":hVL:");
  char         opt;
  uint32_t     secs;
  const char  *z;

  progname = nextopt_progname(&nopt);
  while((opt = nextopt(&nopt))){
      char optc[2] = {nopt.opt_got, '\0'};
      switch(opt){
      case 'h': usage(); die(0); break;
      case 'V': version(); die(0); break;
      case 'L': /* label string ignored */ break;
      case ':':
          fatal_usage("missing argument for option -", optc);
          break;
      case '?':
          if(nopt.opt_got != '?'){
              fatal_usage("invalid option: -", optc);
          }
          /* else fallthrough: */
      default :
          die_usage(); break; 
      }
  }

  argc -= nopt.arg_ndx;
  argv += nopt.arg_ndx;

  if(argc < 2){
      fatal_usage("missing required argument(s)");
  }

  z = nuscan_uint32(&secs, argv[0]);
  if(*z != '\0'){
      fatal_usage("bad numeric argument for secs: ", argv[0]);
  }
  ++argv;

  /* catch SIGALRM on pause()/sleep() without termination: */
  sig_catch(SIGALRM, sig_trap);

  if(secs == 0)
      pause();
  else
      sleep(secs);

  sig_uncatch(SIGALRM);
  errno = 0; 

  /* execvx() provides path search for prog */
  execvx(argv[0], argv, envp, NULL);

  /* uh oh: */
  fatal_syserr("unable to run ", argv[0]);

  /* not reached: */
  return 0;
}