diff options
author | Waldemar Brodkorb <wbx@openadk.org> | 2014-08-20 21:11:13 +0200 |
---|---|---|
committer | Waldemar Brodkorb <wbx@openadk.org> | 2014-08-26 12:29:24 +0200 |
commit | 8e2707b81b0c90295c9fdf92a576925442d22147 (patch) | |
tree | e95ad185bfb7169ddaa1cfdceb6a9b134b3ec8b8 | |
parent | 62f5a17a49e65c6639460abbf352b158b36301a7 (diff) |
add sash, simpleinit and a uclibc config for nonmmu case
31 files changed, 5416 insertions, 44 deletions
diff --git a/mk/image.mk b/mk/image.mk index 321794f76..e47a82ac1 100644 --- a/mk/image.mk +++ b/mk/image.mk @@ -6,6 +6,8 @@ ifeq (${ADK_BINSH_ASH},y) BINSH:=ash else ifeq (${ADK_BINSH_BASH},y) BINSH:=bash +else ifeq (${ADK_BINSH_SASH},y) +BINSH:=sash else ifeq (${ADK_BINSH_HUSH},y) BINSH:=hush else ifeq (${ADK_BINSH_MKSH},y) @@ -21,6 +23,8 @@ ifeq (${ADK_ROOTSH_ASH},y) ROOTSH:=/bin/ash else ifeq (${ADK_ROOTSH_BASH},y) ROOTSH:=/bin/bash +else ifeq (${ADK_ROOTSH_SASH},y) +ROOTSH:=/bin/sash else ifeq (${ADK_ROOTSH_HUSH},y) ROOTSH:=/bin/hush else ifeq (${ADK_ROOTSH_MKSH},y) @@ -54,9 +58,13 @@ image-prepare-post: mkfontdir ${TARGET_DIR}/usr/share/fonts/X11/$${i}; \ done; \ fi +ifeq (${ADK_ROOTSH_SASH},) $(SED) '/^root:/s!:/bin/sh$$!:${ROOTSH}!' ${TARGET_DIR}/etc/passwd +endif +ifeq (${ADK_BINSH_SASH},) -rm -f ${TARGET_DIR}/bin/sh ln -sf ${BINSH} ${TARGET_DIR}/bin/sh +endif test -z $(GIT) || \ $(GIT) log -1|head -1|sed -e 's#commit ##' \ > $(TARGET_DIR)/etc/.adkversion diff --git a/package/busybox/config/init/Config.in b/package/busybox/config/init/Config.in index d8b4a449e..58ab4bca4 100644 --- a/package/busybox/config/init/Config.in +++ b/package/busybox/config/init/Config.in @@ -44,6 +44,7 @@ config BUSYBOX_FEATURE_BOOTCHARTD_CONFIG_FILE help Enable reading and parsing of $PWD/bootchartd.conf and /etc/bootchartd.conf files. + config BUSYBOX_HALT bool "poweroff, halt, and reboot" default y @@ -69,9 +70,11 @@ config BUSYBOX_TELINIT_PATH When busybox halt and friends have to call external telinit to facilitate proper shutdown, this path is to be used when locating telinit executable. + config BUSYBOX_INIT bool "init" default y + depends on !ADK_TARGET_UCLINUX select BUSYBOX_FEATURE_SYSLOG help init is the first program run when the system boots. diff --git a/package/busybox/config/shell/Config.in b/package/busybox/config/shell/Config.in index b1b8ad4b2..dd396b015 100644 --- a/package/busybox/config/shell/Config.in +++ b/package/busybox/config/shell/Config.in @@ -299,7 +299,7 @@ config BUSYBOX_MSH choice prompt "Choose which shell is aliased to 'sh' name" - default FEATURE_SH_IS_ASH + default FEATURE_SH_IS_NONE help Choose which shell you want to be executed by 'sh' alias. The ash shell is the most bash compatible and full featured one. diff --git a/package/sash/Makefile b/package/sash/Makefile new file mode 100644 index 000000000..16a767a70 --- /dev/null +++ b/package/sash/Makefile @@ -0,0 +1,25 @@ +# This file is part of the OpenADK project. OpenADK is copyrighted +# material, please see the LICENCE file in the top-level directory. + +include ${ADK_TOPDIR}/rules.mk + +PKG_NAME:= sash +PKG_VERSION:= 1.0 +PKG_RELEASE:= 1 +PKG_DESCR:= standalone shell +PKG_SECTION:= base/shells + +NO_DISTFILES:= 1 + +include ${ADK_TOPDIR}/mk/package.mk + +$(eval $(call PKG_template,SASH,sash,${PKG_VERSION}-${PKG_RELEASE},${PKG_DEPENDS},${PKG_DESCR},${PKG_SECTION})) + +CONFIG_STYLE:= manual +INSTALL_STYLE:= manual + +do-install: + ${INSTALL_DIR} ${IDIR_SASH}/bin + ${INSTALL_BIN} ${WRKBUILD}/sh ${IDIR_SASH}/bin/sh + +include ${ADK_TOPDIR}/mk/pkg-bottom.mk diff --git a/package/sash/files/rc b/package/sash/files/rc new file mode 100755 index 000000000..33d60a4b6 --- /dev/null +++ b/package/sash/files/rc @@ -0,0 +1,47 @@ +#!/bin/sh +set -x +export PATH=/bin:/sbin:/usr/bin:/usr/sbin +ln -s /proc/self/fd/2 /dev/stderr +: ${rcquiet=0} +if [ $rcquiet -ne 1 ];then + echo "System initialization ..." +fi + +# remount /dev with smaller size +mount -o remount,nosuid,size=128k,mode=0755 -t tmpfs mdev /dev + +# start mdev dynamic device node management +echo >/dev/mdev.seq +if [ -f /proc/sys/kernel/hotplug ];then + echo "/sbin/mdev" >/proc/sys/kernel/hotplug +fi +# creates f.e. /dev/root +mdev -s + +# seed some random +cat /etc/.rnd >/dev/urandom 2>&1 + +# setup cfgfs +[ -x /sbin/cfgfs ] && { + cfgfs setup + mount -o remount,ro / +} + +# remount /tmp with smaller size +size=$(cat /etc/tmpfs 2>/dev/null) +[ -z $size ] && size=2048 +mount -o remount,nosuid,nodev,mode=1777,size=${size}k -t tmpfs tmpfs /tmp + +# create some useful directories in tmpfs +mkdir -p /var/log +mkdir -p /var/run +mkdir -p /var/tmp +touch /var/log/lastlog +touch /var/log/wtmp + +HOSTNAME= +[[ -s /etc/hostname ]] && HOSTNAME=$(cat /etc/hostname) +HOSTNAME=${HOSTNAME%%.*} +echo ${HOSTNAME:=openadk} >/proc/sys/kernel/hostname + +chown 0:0 /tmp; chmod 1777 /tmp diff --git a/package/sash/src/Makefile b/package/sash/src/Makefile new file mode 100644 index 000000000..90d6adf99 --- /dev/null +++ b/package/sash/src/Makefile @@ -0,0 +1,38 @@ + +SH = sh +SHOBJS = sash.o cmds.o cmd_uclinux.o ls.o hexdump.o df.o free.o \ + hostname.o date.o + +SHUTDOWN = shutdown +SHUTDOWNOBJS = shutdown.o + +REBOOT = reboot +REBOOTOBJS = reboot.o + +SHOBJS += ps.o +CFLAGS += -DCONFIG_USER_SASH_PS + +LIBSASH = libsash/libsash.a + +CFLAGS += -DCOMMAND_HISTORY + +all: $(SH) $(SHUTDOWN) $(REBOOT) + +$(SH): $(SHOBJS) $(LIBSASH) + $(CC) $(LDFLAGS) -o $@ $(SHOBJS) $(LIBSASH) $(LDLIBS$(LDLIBS_$@)) + +$(SHUTDOWN): $(SHUTDOWNOBJS) $(LIBSASH) + $(CC) $(LDFLAGS) -o $@ $(SHUTDOWNOBJS) $(LIBSASH) $(LDLIBS) + +$(REBOOT): $(REBOOTOBJS) $(LIBSASH) + $(CC) $(LDFLAGS) -o $@ $(REBOOTOBJS) $(LIBSASH) $(LDLIBS$(LDLIBS_$@)) + +dummy_target: + +$(LIBSASH): dummy_target + $(MAKE) -C libsash + +clean: + -rm -f $(SH) $(SHUTDOWN) $(REBOOT) *.elf *.gdb *.o + $(MAKE) -C libsash clean + diff --git a/package/sash/src/README b/package/sash/src/README new file mode 100644 index 000000000..191c7de63 --- /dev/null +++ b/package/sash/src/README @@ -0,0 +1,6 @@ + + + This shell is an adaption of David Bell's "sash", the stand-along shell, +with some adaptions (and truncations) for our environment. It also includes +a few utilities (like reboot and ps) that weren't part of the original sash. + diff --git a/package/sash/src/cmd_uclinux.c b/package/sash/src/cmd_uclinux.c new file mode 100644 index 000000000..bf66c4529 --- /dev/null +++ b/package/sash/src/cmd_uclinux.c @@ -0,0 +1,127 @@ + +#include "sash.h" + +#include <fcntl.h> +#include <sys/types.h> + +#include <sys/stat.h> +#include <dirent.h> +#include <pwd.h> +#include <grp.h> +#include <time.h> +#include <unistd.h> + +#if 0 +char psbuf[256]; +char name[40]; +int pid, state; +char statec; + +void +do_ps(argc, argv) + char **argv; +{ + int i; + int h; + int max; + FILE * f; + DIR * d; + struct dirent * de; + int l; + + printf(" PID TTY STAT TIME COMMAND\n"); + + + d = opendir("/proc"); + if (!d) + return; + + while (de = readdir(d)) { + for(i=0;i<strlen(de->d_name);i++) + if (!isdigit(de->d_name[i])) + goto next; + + sprintf(psbuf, "/proc/%s/stat", de->d_name); + h = open(psbuf, O_RDONLY); + + if (h==-1) + continue; + + l = read(h, psbuf, 255); + if (l<=0) { + perror("Unable to read status"); + close(h); + continue; + } + + psbuf[l] = '\0'; + psbuf[255] = '\0'; + + + if (sscanf(psbuf, + "%d %s %c", + &pid, name, &statec)<3) + { + perror("Unable to parse status"); + close(h); + continue; + } + + state = statec; + + close(h); + + sprintf(psbuf, "/proc/%s/cmdline", de->d_name); + h = open(psbuf, O_RDONLY); + + if (h == -1) { + perror("Unable to open cmdline"); + continue; + } + + l = read(h, psbuf, 255); + if (l < 0) { + perror("Unable to read cmdline"); + close(h); + continue; + } + + close(h); + + psbuf[255] = psbuf[l] = '\0'; + + printf("%5d %3s %c --:-- %s\n", pid, "", state, psbuf); + next: + } + + closedir(d); +} +#endif + +void +do_cat(argc, argv) + char **argv; +{ + int fd; + char *name; + size_t l; + char buf[256]; + + while (argc-- > 1) { + if (intflag) { + return; + } + name = *(++argv); + + fd = open(name, O_RDONLY); + if (fd < 0) { + perror(name); + return; + } + + while ((l = read(fd, buf, sizeof(buf))) > 0) { + fwrite(buf, 1, l, stdout); + } + close(fd); + } +} diff --git a/package/sash/src/cmds.c b/package/sash/src/cmds.c new file mode 100644 index 000000000..d822d9f6d --- /dev/null +++ b/package/sash/src/cmds.c @@ -0,0 +1,899 @@ +/* + * Modifications for uClinux + * Copyright (C) 1998 Kenneth Albanowski <kjahds@kjahds.com> + * + * Original code + * Copyright (c) 1993 by David I. Bell + * Permission is granted to use, distribute, or modify this source, + * provided that this copyright notice remains intact. + * + * Most simple built-in commands are here. + */ + +#include "sash.h" + +#include <sys/types.h> +#include <sys/stat.h> +#include <sys/time.h> +#include <unistd.h> +#include <fcntl.h> +#include <signal.h> +#include <pwd.h> +#include <grp.h> +#include <utime.h> +#include <errno.h> +#ifdef EMBED +#include <config/autoconf.h> +#endif + +void +do_echo(argc, argv) + char **argv; +{ + BOOL first; + + first = TRUE; + while (argc-- > 1) { + if (!first) + fputc(' ', stdout); + first = FALSE; + fputs(*++argv, stdout); + } + fputc('\n', stdout); +} + + +void +do_pwd(argc, argv) + char **argv; +{ + char buf[PATHLEN]; + + if (getcwd(buf, PATHLEN) == NULL) { + fprintf(stderr, "Cannot get current directory\n"); + return; + } + + printf("%s\n", buf); +} + +void +do_time(argc, argv) + char ** argv; +{ + struct timeval tv; + gettimeofday(&tv, 0); + printf("Time of day = %d.%6.6d seconds\n", tv.tv_sec, tv.tv_usec); +} + +void +do_cd(argc, argv) + char **argv; +{ + char *path; + + if (argc > 1) + path = argv[1]; + else { + path = getenv("HOME"); + if (path == NULL) { + fprintf(stderr, "No HOME environment variable\n"); + return; + } + } + + if (chdir(path) < 0) + perror(path); +} + + +void +do_mkdir(argc, argv) + char **argv; +{ + int state = 0, mode = -1; + + while (argc-- > 1) { + if (state == 0) { + if (strcmp(argv[1], "-m") == 0) + state = 1; + else if (mkdir(argv[1], 0777) < 0) + perror(argv[1]); + else if (mode != -1 && chmod(argv[1], mode) < 0) + perror(argv[1]); + } else if (state == 1) { + mode = strtol(argv[1], NULL, 8); + state = 0; + } + argv++; + } +} + +void +do_sleep(argc, argv) + char **argv; +{ + if (argc > 1) + sleep(atoi(argv[1])); +} + +void +do_mknod(argc, argv) + char **argv; +{ + char *cp; + int mode; + int major; + int minor; + + mode = 0666; + + if (strcmp(argv[2], "b") == 0) + mode |= S_IFBLK; + else if (strcmp(argv[2], "c") == 0) + mode |= S_IFCHR; + else { + fprintf(stderr, "Bad device type\n"); + return; + } + + major = 0; + cp = argv[3]; + while (isdecimal(*cp)) + major = major * 10 + *cp++ - '0'; + + if (*cp || (major < 0) || (major > 255)) { + fprintf(stderr, "Bad major number\n"); + return; + } + + minor = 0; + cp = argv[4]; + while (isdecimal(*cp)) + minor = minor * 10 + *cp++ - '0'; + + if (*cp || (minor < 0) || (minor > 255)) { + fprintf(stderr, "Bad minor number\n"); + return; + } + + if (mknod(argv[1], mode, major * 256 + minor) < 0) + perror(argv[1]); +} + + +void +do_rmdir(argc, argv) + char **argv; +{ + while (argc-- > 1) { + if (rmdir(argv[1]) < 0) + perror(argv[1]); + argv++; + } +} + + +void +do_sync(argc, argv) + char **argv; +{ +#ifdef CONFIG_USER_FLATFSD_FLATFSD + system("exec flatfsd -s"); +#endif + sync(); +} + + +void +do_rm(argc, argv) + char **argv; +{ + while (argc-- > 1) { + if (unlink(argv[1]) < 0) + perror(argv[1]); + argv++; + } +} + + +void +do_chmod(argc, argv) + char **argv; +{ + char *cp; + int mode; + + mode = 0; + cp = argv[1]; + while (isoctal(*cp)) + mode = mode * 8 + (*cp++ - '0'); + + if (*cp) { + fprintf(stderr, "Mode must be octal\n"); + return; + } + argc--; + argv++; + + while (argc-- > 1) { + if (chmod(argv[1], mode) < 0) + perror(argv[1]); + argv++; + } +} + + +void +do_chown(argc, argv) + char **argv; +{ + char *cp; + int uid; + struct passwd *pwd; + struct stat statbuf; + + cp = argv[1]; + if (isdecimal(*cp)) { + uid = 0; + while (isdecimal(*cp)) + uid = uid * 10 + (*cp++ - '0'); + + if (*cp) { + fprintf(stderr, "Bad uid value\n"); + return; + } + } else { + pwd = getpwnam(cp); + if (pwd == NULL) { + fprintf(stderr, "Unknown user name\n"); + return; + } + + uid = pwd->pw_uid; + } + + argc--; + argv++; + + while (argc-- > 1) { + argv++; + if ((stat(*argv, &statbuf) < 0) || + (chown(*argv, uid, statbuf.st_gid) < 0)) + perror(*argv); + } +} + + +void +do_chgrp(argc, argv) + char **argv; +{ + char *cp; + int gid; + struct group *grp; + struct stat statbuf; + + cp = argv[1]; + if (isdecimal(*cp)) { + gid = 0; + while (isdecimal(*cp)) + gid = gid * 10 + (*cp++ - '0'); + + if (*cp) { + fprintf(stderr, "Bad gid value\n"); + return; + } + } else { + grp = getgrnam(cp); + if (grp == NULL) { + fprintf(stderr, "Unknown group name\n"); + return; + } + + gid = grp->gr_gid; + } + + argc--; + argv++; + + while (argc-- > 1) { + argv++; + if ((stat(*argv, &statbuf) < 0) || + (chown(*argv, statbuf.st_uid, gid) < 0)) + perror(*argv); + } +} + + +void +do_touch(argc, argv) + char **argv; +{ + char *name; + int fd; + struct utimbuf now; + + time(&now.actime); + now.modtime = now.actime; + + while (argc-- > 1) { + name = *(++argv); + + if (utime(name, &now) <0) + { + fd = open(name, O_CREAT | O_WRONLY | O_EXCL, 0666); + if (fd >= 0) + { + close(fd); + continue; + } + perror(name); + } + } +} + + +void +do_mv(argc, argv) + char **argv; +{ + int dirflag; + char *srcname; + char *destname; + char *lastarg; + + lastarg = argv[argc - 1]; + + dirflag = isadir(lastarg); + + if ((argc > 3) && !dirflag) { + fprintf(stderr, "%s: not a directory\n", lastarg); + return; + } + + while (argc-- > 2) { + srcname = *(++argv); + if (access(srcname, 0) < 0) { + perror(srcname); + continue; + } + + destname = lastarg; + if (dirflag) + destname = buildname(destname, srcname); + + if (rename(srcname, destname) >= 0) + continue; + + if (errno != EXDEV) { + perror(destname); + continue; + } + + if (!copyfile(srcname, destname, TRUE)) + continue; + + if (unlink(srcname) < 0) + perror(srcname); + } +} + + +void +do_ln(argc, argv) + char **argv; +{ + int dirflag; + char *srcname; + char *destname; + char *lastarg; + + if (argv[1][0] == '-') { + if (strcmp(argv[1], "-s")) { + fprintf(stderr, "Unknown option\n"); + return; + } + + if (argc != 4) { + fprintf(stderr, "Wrong number of arguments for symbolic link\n"); + return; + } + +#ifdef S_ISLNK + if (symlink(argv[2], argv[3]) < 0) + perror(argv[3]); +#else + fprintf(stderr, "Symbolic links are not allowed\n"); +#endif + return; + } + + /* + * Here for normal hard links. + */ + lastarg = argv[argc - 1]; + dirflag = isadir(lastarg); + + if ((argc > 3) && !dirflag) { + fprintf(stderr, "%s: not a directory\n", lastarg); + return; + } + + while (argc-- > 2) { + srcname = *(++argv); + if (access(srcname, 0) < 0) { + perror(srcname); + continue; + } + + destname = lastarg; + if (dirflag) + destname = buildname(destname, srcname); + + if (link(srcname, destname) < 0) { + perror(destname); + continue; + } + } +} + + +void +do_cp(argc, argv) + char **argv; +{ + BOOL dirflag; + char *srcname; + char *destname; + char *lastarg; + + lastarg = argv[argc - 1]; + + dirflag = isadir(lastarg); + + if ((argc > 3) && !dirflag) { + fprintf(stderr, "%s: not a directory\n", lastarg); + return; + } + + while (argc-- > 2) { + destname = lastarg; + srcname = *++argv; + if (dirflag) + destname = buildname(destname, srcname); + + (void) copyfile(srcname, destname, FALSE); + } +} + + +void +do_mount(argc, argv) + char **argv; +{ + char *str; + char *type; + + argc--; + argv++; + type = "minix"; + + while ((argc > 0) && (**argv == '-')) { + argc--; + str = *argv++ ; + + while (*++str) switch (*str) { + case 't': + if ((argc <= 0) || (**argv == '-')) { + fprintf(stderr, "Missing file system type\n"); + return; + } + + type = *argv++; + argc--; + break; + + default: + fprintf(stderr, "Unknown option\n"); + return; + } + } + + if (argc != 2) { + fprintf(stderr, "Wrong number of arguments for mount\n"); + return; + } + + if (mount(argv[0], argv[1], type, 0, 0) < 0) + perror("mount failed"); +} + + +void +do_umount(argc, argv) + char **argv; +{ + if (umount(argv[1]) < 0) + perror(argv[1]); +} + + +void +do_cmp(argc, argv) + char **argv; +{ + int fd1; + int fd2; + int cc1; + int cc2; + long pos; + char *srcname; + char *destname; + char *lastarg; + char *bp1; + char *bp2; + char *buf1; + char *buf2; + struct stat statbuf1; + struct stat statbuf2; + + if (stat(argv[1], &statbuf1) < 0) { + perror(argv[1]); + return; + } + + if (stat(argv[2], &statbuf2) < 0) { + perror(argv[2]); + return; + } + + if ((statbuf1.st_dev == statbuf2.st_dev) && + (statbuf1.st_ino == statbuf2.st_ino)) + { + printf("Files are links to each other\n"); + return; + } + + if (statbuf1.st_size != statbuf2.st_size) { + printf("Files are different sizes\n"); + return; + } + + fd1 = open(argv[1], 0); + if (fd1 < 0) { + perror(argv[1]); + return; + } + + fd2 = open(argv[2], 0); + if (fd2 < 0) { + perror(argv[2]); + close(fd1); + return; + } + + buf1 = malloc(8192-16); + buf2 = malloc(8192-16); + + pos = 0; + while (TRUE) { + if (intflag) + goto closefiles; + + cc1 = read(fd1, buf1, 8192-16); + if (cc1 < 0) { + perror(argv[1]); + goto closefiles; + } + + cc2 = read(fd2, buf2, 8192-16); + if (cc2 < 0) { + perror(argv[2]); + goto closefiles; + } + + if ((cc1 == 0) && (cc2 == 0)) { + printf("Files are identical\n"); + goto closefiles; + } + + if (cc1 < cc2) { + printf("First file is shorter than second\n"); + goto closefiles; + } + + if (cc1 > cc2) { + printf("Second file is shorter than first\n"); + goto closefiles; + } + + if (memcmp(buf1, buf2, cc1) == 0) { + pos += cc1; + continue; + } + + bp1 = buf1; + bp2 = buf2; + while (*bp1++ == *bp2++) + pos++; + + printf("Files differ at byte position %ld\n", pos); + goto closefiles; + } + +closefiles: + close(fd1); + close(fd2); + free(buf1); + free(buf2); +} + + +void +do_more(argc, argv) + char **argv; +{ + FILE *fp; + char *name; + int ch; + int line; + int col; + char buf[80]; + + while (argc-- > 1) { + name = *(++argv); + + fp = fopen(name, "r"); + if (fp == NULL) { + perror(name); + return; + } + + printf("<< %s >>\n", name); + line = 1; + col = 0; + + while (fp && ((ch = fgetc(fp)) != EOF)) { + switch (ch) { + case '\r': + col = 0; + break; + + case '\n': + line++; + col = 0; + break; + + case '\t': + col = ((col + 1) | 0x07) + 1; + break; + + case '\b': + if (col > 0) + col--; + break; + + default: + col++; + } + + putchar(ch); + if (col >= 80) { + col -= 80; + line++; + } + + if (line < 24) + continue; + + if (col > 0) + putchar('\n'); + + printf("--More--"); + fflush(stdout); + + if (intflag || (read(0, buf, sizeof(buf)) < 0)) { + if (fp) + fclose(fp); + return; + } + + ch = buf[0]; + if (ch == ':') + ch = buf[1]; + + switch (ch) { + case 'N': + case 'n': + fclose(fp); + fp = NULL; + break; + + case 'Q': + case 'q': + fclose(fp); + return; + } + + col = 0; + line = 1; + } + if (fp) + fclose(fp); + } +} + + +void +do_exit(argc, argv) + char **argv; +{ + exit(0); +} + + +void +do_setenv(argc, argv) + char **argv; +{ + setenv(argv[1], argv[2], 1); +} + + +void +do_printenv(argc, argv) + char **argv; +{ + char **env; + extern char **environ; + int len; + + env = environ; + + if (argc == 1) { + while (*env) + printf("%s\n", *env++); + return; + } + + len = strlen(argv[1]); + while (*env) { + if ((strlen(*env) > len) && (env[0][len] == '=') && + (memcmp(argv[1], *env, len) == 0)) + { + printf("%s\n", &env[0][len+1]); + return; + } + env++; + } +} + + +void +do_umask(argc, argv) + char **argv; +{ + char *cp; + int mask; + + if (argc <= 1) { + mask = umask(0); + umask(mask); + printf("%03o\n", mask); + return; + } + + mask = 0; + cp = argv[1]; + while (isoctal(*cp)) + mask = mask * 8 + *cp++ - '0'; + + if (*cp || (mask & ~0777)) { + fprintf(stderr, "Bad umask value\n"); + return; + } + + umask(mask); +} +< |