service.c revision db397771158a0b9b33b5ab2dee8593e03ee5e994
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync/*
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * CDDL HEADER START
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * The contents of this file are subject to the terms of the
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * Common Development and Distribution License, Version 1.0 only
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * (the "License"). You may not use this file except in compliance
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * with the License.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * or http://www.opensolaris.org/os/licensing.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * See the License for the specific language governing permissions
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * and limitations under the License.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * When distributing Covered Code, include this CDDL HEADER in each
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * If applicable, add the following below this CDDL HEADER, with the
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * fields enclosed by brackets "[]" replaced with your own identifying
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * information: Portions Copyright [yyyy] [name of copyright owner]
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * CDDL HEADER END
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync/*
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * Copyright 2003 Sun Microsystems, Inc. All rights reserved.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * Use is subject to license terms.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync/* Copyright (c) 1984, 1986, 1987, 1988, 1989 AT&T */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync/* All Rights Reserved */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync#pragma ident "%Z%%M% %I% %E% SMI"
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync/*
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * UNIX shell
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync#include "defs.h"
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync#include <errno.h>
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync#include <fcntl.h>
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync#include "sh_policy.h"
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync#define ARGMK 01
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncstatic unsigned char *execs();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncstatic void gsort();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncstatic int split();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncextern void makearg(struct argnod *);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncextern const char *sysmsg[];
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncextern short topfd;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync/*
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * service routines for `execute'
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncshort
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncinitio(struct ionod *iop, int save)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync{
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char *ion;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync int iof, fd;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync int ioufd;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync short lastfd;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync int newmode;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync lastfd = topfd;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync while (iop) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync iof = iop->iofile;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync ion = mactrim(iop->ioname);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync ioufd = iof & IOUFD;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (*ion && (flags&noexec) == 0) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (save) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fdmap[topfd].org_fd = ioufd;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fdmap[topfd++].dup_fd = savefd(ioufd);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (iof & IODOC) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync struct tempblk tb;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync subst(chkopen(ion, 0), (fd = tmpfil(&tb)));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync /*
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * pushed in tmpfil() --
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * bug fix for problem with
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * in-line scripts
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync poptemp();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fd = chkopen(tmpout, 0);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unlink((const char *)tmpout);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync } else if (iof & IOMOV) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (eq(minus, ion)) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fd = -1;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync close(ioufd);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync } else if ((fd = stoi(ion)) >= USERIO) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync failed(ion, badfile);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync else
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fd = dup(fd);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync } else if (((iof & IOPUT) == 0) && ((iof & IORDW) == 0))
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fd = chkopen(ion, 0);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync else if (iof & IORDW) /* For <> */ {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync newmode = O_RDWR|O_CREAT;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fd = chkopen(ion, newmode);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync } else if (flags & rshflg) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync failed(ion, restricted);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync } else if (iof & IOAPP &&
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync (fd = open((char *)ion, 1)) >= 0) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync lseek(fd, (off_t)0, SEEK_END);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync } else {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fd = create(ion);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (fd >= 0)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync renamef(fd, ioufd);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync iop = iop->ionxt;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return (lastfd);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync}
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncunsigned char *
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncsimple(s)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncunsigned char *s;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync{
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char *sname;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync sname = s;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync while (1) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (any('/', sname))
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync while (*sname++ != '/')
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync ;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync else
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return (sname);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync}
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncunsigned char *
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncgetpath(s)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char *s;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync{
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char *path, *newpath;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync int pathlen;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (any('/', s))
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (flags & rshflg)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync failed(s, restricted);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync else
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return ((unsigned char *)nullstr);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync } else if ((path = pathnod.namval) == 0)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return ((unsigned char *)defpath);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync else {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync pathlen = length(path)-1;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync /* Add extra ':' if PATH variable ends in ':' */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (pathlen > 2 && path[pathlen - 1] == ':' &&
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync path[pathlen - 2] != ':') {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync newpath = locstak();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync (void) memcpystak(newpath, path, pathlen);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync newpath[pathlen] = ':';
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync endstak(newpath + pathlen + 1);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return (newpath);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync } else
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return (cpystak(path));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync}
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncint
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncpathopen(unsigned char *path, unsigned char *name)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync{
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync int f;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync do
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync path = catpath(path, name);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync } while ((f = open((char *)curstak(), 0)) < 0 && path);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return (f);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync}
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncunsigned char *
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsynccatpath(unsigned char *path, unsigned char *name)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync{
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync /*
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * leaves result on top of stack
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char *scanp = path;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char *argp = locstak();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync while (*scanp && *scanp != COLON) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (argp >= brkend)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync growstak(argp);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *argp++ = *scanp++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (scanp != path) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (argp >= brkend)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync growstak(argp);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *argp++ = '/';
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (*scanp == COLON)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync scanp++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync path = (*scanp ? scanp : 0);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync scanp = name;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync do
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (argp >= brkend)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync growstak(argp);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync while (*argp++ = *scanp++);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return (path);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync}
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncunsigned char *
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncnextpath(unsigned char *path)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync{
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char *scanp = path;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync while (*scanp && *scanp != COLON)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync scanp++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (*scanp == COLON)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync scanp++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return (*scanp ? scanp : 0);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync}
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncstatic const char *xecmsg;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncstatic unsigned char **xecenv;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncvoid
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncexeca(unsigned char *at[], short pos)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync{
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char *path;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char **t = at;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync int cnt;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if ((flags & noexec) == 0) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync xecmsg = notfound;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync path = getpath(*t);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync xecenv = local_setenv();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (pos > 0) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync cnt = 1;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync while (cnt != pos) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync ++cnt;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync path = nextpath(path);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync execs(path, t);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync path = getpath(*t);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync while (path = execs(path, t))
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync ;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync failed(*t, xecmsg);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync}
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncstatic unsigned char *
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncexecs(unsigned char *ap, unsigned char *t[])
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync{
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync int pfstatus = NOATTRS;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char *p, *prefix;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char *savptr;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync prefix = catpath(ap, t[0]);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync trim(p = curstak());
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync sigchk();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (flags & pfshflg) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync /*
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * Need to save the stack information, or the
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * first memory allocation in secpolicy_profile_lookup()
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * will clobber it.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync savptr = endstak(p + strlen((const char *)p) + 1);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync pfstatus = secpolicy_pfexec((const char *)p,
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync (char **)t, (const char **)xecenv);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (pfstatus != NOATTRS) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync errno = pfstatus;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync tdystak(savptr);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (pfstatus == NOATTRS) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync execve((const char *)p, (char *const *)&t[0],
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync (char *const *)xecenv);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync switch (errno) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync case ENOEXEC: /* could be a shell script */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync funcnt = 0;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync flags = 0;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *flagadr = 0;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync comdiv = 0;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync ioset = 0;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync clearup(); /* remove open files and for loop junk */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (input)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync close(input);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync input = chkopen(p, 0);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync#ifdef ACCT
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync preacct(p); /* reset accounting */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync#endif
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync /*
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * set up new args
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync setargs(t);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync longjmp(subshell, 1);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync case ENOMEM:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync failed(p, toobig);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync case E2BIG:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync failed(p, arglist);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync case ETXTBSY:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync failed(p, txtbsy);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync case ELIBACC:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync failed(p, libacc);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync case ELIBBAD:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync failed(p, libbad);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync case ELIBSCN:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync failed(p, libscn);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync case ELIBMAX:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync failed(p, libmax);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync default:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync xecmsg = badexec;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync case ENOENT:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return (prefix);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync}
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncBOOL nosubst;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncvoid
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsynctrim(unsigned char *at)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync{
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char *last;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char *current;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char c;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync int len;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync wchar_t wc;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync nosubst = 0;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (current = at) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync last = at;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync while (c = *current) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if ((len = mbtowc(&wc, (char *)current,
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync MB_LEN_MAX)) <= 0) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *last++ = c;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync current++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync continue;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (wc != '\\') {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync memcpy(last, current, len);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync last += len;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync current += len;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync continue;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync /* remove \ and quoted nulls */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync nosubst = 1;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync current++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (c = *current) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if ((len = mbtowc(&wc, (char *)current,
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync MB_LEN_MAX)) <= 0) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *last++ = c;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync current++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync continue;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync memcpy(last, current, len);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync last += len;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync current += len;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync } else
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync current++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *last = 0;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync}
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync/* Same as trim, but only removes backlashes before slashes */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncvoid
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsynctrims(at)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncunsigned char *at;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync{
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char *last;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char *current;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char c;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync int len;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync wchar_t wc;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (current = at)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync last = at;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync while (c = *current) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if ((len = mbtowc(&wc, (char *)current,
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync MB_LEN_MAX)) <= 0) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *last++ = c;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync current++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync continue;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (wc != '\\') {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync memcpy(last, current, len);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync last += len; current += len;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync continue;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync /* remove \ and quoted nulls */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync current++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (!(c = *current)) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync current++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync continue;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (c == '/') {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *last++ = c;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync current++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync continue;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *last++ = '\\';
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if ((len = mbtowc(&wc, (char *)current,
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync MB_LEN_MAX)) <= 0) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *last++ = c;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync current++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync continue;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync memcpy(last, current, len);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync last += len; current += len;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *last = 0;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync}
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncunsigned char *
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncmactrim(s)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncunsigned char *s;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync{
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char *t = macro(s);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync trim(t);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return (t);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync}
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncunsigned char **
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncscan(argn)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncint argn;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync{
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync struct argnod *argp =
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync (struct argnod *)(Rcheat(gchain) & ~ARGMK);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char **comargn, **comargm;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync comargn = (unsigned char **)getstak(BYTESPERWORD * argn + BYTESPERWORD);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync comargm = comargn += argn;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *comargn = ENDARGS;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync while (argp)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *--comargn = argp->argval;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync trim(*comargn);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync argp = argp->argnxt;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (argp == 0 || Rcheat(argp) & ARGMK)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync gsort(comargn, comargm);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync comargm = comargn;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync argp = (struct argnod *)(Rcheat(argp) & ~ARGMK);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return (comargn);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync}
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncstatic void
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncgsort(from, to)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncunsigned char *from[], *to[];
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync{
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync int k, m, n;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync int i, j;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if ((n = to - from) <= 1)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync for (j = 1; j <= n; j *= 2)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync ;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync for (m = 2 * j - 1; m /= 2; )
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync k = n - m;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync for (j = 0; j < k; j++)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync for (i = j; i >= 0; i -= m)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char **fromi;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fromi = &from[i];
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (cf(fromi[m], fromi[0]) > 0)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync break;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync else
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char *s;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync s = fromi[m];
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fromi[m] = fromi[0];
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fromi[0] = s;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync}
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync/*
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * Argument list generation
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncint
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncgetarg(ac)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncstruct comnod *ac;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync{
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync struct argnod *argp;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync int count = 0;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync struct comnod *c;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (c = ac)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync argp = c->comarg;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync while (argp)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync count += split(macro(argp->argval), 1);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync argp = argp->argnxt;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return (count);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync}
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncstatic int
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncsplit(s) /* blank interpretation routine */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncunsigned char *s;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync{
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char *argp;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync int c;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync int count = 0;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync for (;;)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync int length;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync sigchk();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync argp = locstak() + BYTESPERWORD;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync while (c = *s) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync wchar_t wc;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if ((length = mbtowc(&wc, (char *)s,
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync MB_LEN_MAX)) <= 0) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync wc = (unsigned char)*s;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync length = 1;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (c == '\\') { /* skip over quoted characters */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (argp >= brkend)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync growstak(argp);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *argp++ = c;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync s++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync /* get rest of multibyte character */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if ((length = mbtowc(&wc, (char *)s,
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync MB_LEN_MAX)) <= 0) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync wc = (unsigned char)*s;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync length = 1;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (argp >= brkend)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync growstak(argp);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *argp++ = *s++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync while (--length > 0) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (argp >= brkend)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync growstak(argp);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *argp++ = *s++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync continue;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (anys(s, ifsnod.namval)) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync /* skip to next character position */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync s += length;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync break;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (argp >= brkend)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync growstak(argp);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *argp++ = c;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync s++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync while (--length > 0) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (argp >= brkend)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync growstak(argp);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync *argp++ = *s++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (argp == staktop + BYTESPERWORD)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (c)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync continue;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync else
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return (count);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync /*
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * file name generation
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync argp = endstak(argp);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync trims(((struct argnod *)argp)->argval);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if ((flags & nofngflg) == 0 &&
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync (c = expand(((struct argnod *)argp)->argval, 0)))
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync count += c;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync else
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync makearg((struct argnod *)argp);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync count++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync gchain = (struct argnod *)((int)gchain | ARGMK);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync}
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync#ifdef ACCT
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync#include <sys/types.h>
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync#include <sys/acct.h>
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync#include <sys/times.h>
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncstruct acct sabuf;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncstruct tms buffer;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncstatic clock_t before;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncstatic int shaccton; /* 0 implies do not write record on exit */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync /* 1 implies write acct record on exit */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncstatic comp_t compress(clock_t);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync/*
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * suspend accounting until turned on by preacct()
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncvoid
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncsuspacct(void)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync{
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync shaccton = 0;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync}
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncvoid
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncpreacct(unsigned char *cmdadr)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync{
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync unsigned char *simple();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (acctnod.namval && *acctnod.namval) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync sabuf.ac_btime = time((time_t *)0);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync before = times(&buffer);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync sabuf.ac_uid = getuid();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync sabuf.ac_gid = getgid();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync movstrn(simple(cmdadr), sabuf.ac_comm, sizeof (sabuf.ac_comm));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync shaccton = 1;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync}
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncvoid
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncdoacct(void)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync{
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync int fd;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync clock_t after;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (shaccton) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync after = times(&buffer);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync sabuf.ac_utime = compress(buffer.tms_utime + buffer.tms_cutime);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync sabuf.ac_stime = compress(buffer.tms_stime + buffer.tms_cstime);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync sabuf.ac_etime = compress(after - before);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if ((fd = open((char *)acctnod.namval,
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync O_WRONLY | O_APPEND | O_CREAT, 0666)) != -1) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync write(fd, &sabuf, sizeof (sabuf));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync close(fd);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync}
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync/*
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * Produce a pseudo-floating point representation
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync * with 3 bits base-8 exponent, 13 bits fraction
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync */
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncstatic comp_t
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsynccompress(clock_t t)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync{
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync int exp = 0;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync int rund = 0;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync while (t >= 8192) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync exp++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync rund = t & 04;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync t >>= 3;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (rund) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync t++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if (t >= 8192) {
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync t >>= 3;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync exp++;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync }
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return ((exp << 13) + t);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync}
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync#endif
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync