예제 #1
0
파일: rm.c 프로젝트: dezelin/kBuild
static int
check(char *path, char *name, struct stat *sp)
{
	int ch, first;
	char modep[15], *flagsp;

	/* Check -i first. */
	if (iflag)
		(void)fprintf(stderr, "remove %s? ", path);
	else {
		/*
		 * If it's not a symbolic link and it's unwritable and we're
		 * talking to a terminal, ask.  Symbolic links are excluded
		 * because their permissions are meaningless.  Check stdin_ok
		 * first because we may not have stat'ed the file.
		 * Also skip this check if the -P option was specified because
		 * we will not be able to overwrite file contents and will
		 * barf later.
		 */
		if (!stdin_ok || S_ISLNK(sp->st_mode) || Pflag ||
		    (!access(name, W_OK) &&
#ifdef SF_APPEND
		    !(sp->st_flags & (SF_APPEND|SF_IMMUTABLE)) &&
		    (!(sp->st_flags & (UF_APPEND|UF_IMMUTABLE)) || !uid))
#else
                    1)
#endif
                    )
			return (1);
		bsd_strmode(sp->st_mode, modep);
#ifdef SF_APPEND
		if ((flagsp = fflagstostr(sp->st_flags)) == NULL)
			exit(err(1, "fflagstostr"));
		(void)fprintf(stderr, "override %s%s%s/%s %s%sfor %s? ",
		              modep + 1, modep[9] == ' ' ? "" : " ",
		              user_from_uid(sp->st_uid, 0),
		              group_from_gid(sp->st_gid, 0),
		              *flagsp ? flagsp : "", *flagsp ? " " : "",
		              path);
		free(flagsp);
#else
		(void)flagsp;
		(void)fprintf(stderr, "override %s%s %d/%d for %s? ",
		              modep + 1, modep[9] == ' ' ? "" : " ",
		              sp->st_uid, sp->st_gid, path);
#endif
	}
	(void)fflush(stderr);

	first = ch = getchar();
	while (ch != '\n' && ch != EOF)
		ch = getchar();
	return (first == 'y' || first == 'Y');
}
예제 #2
0
파일: stat.c 프로젝트: edgar-pek/PerspicuOS
/*
 * fflagstostr() wrapper that leaks only once
 */
char *
xfflagstostr(unsigned long fflags)
{
	static char *str = NULL;

	if (str != NULL)
		free(str);

	str = fflagstostr(fflags);
	if (str == NULL)
		err(1, "fflagstostr");
	return (str);
}
예제 #3
0
char *
flags_to_string(u_long fflags)
{
	char *string;

	string = fflagstostr(fflags);
	if (string != NULL && *string == '\0') {
		free(string);
		string = strdup("none");
	}
	if (string == NULL)
		err(1, NULL);

	return string;
}
예제 #4
0
파일: rm.c 프로젝트: hmatyschok/MeshBSD
static int
check(const char *path, const char *name, struct stat *sp)
{
    int ch, first;
    char modep[15], *flagsp;

    /* Check -i first. */
    if (iflag)
        (void)fprintf(stderr, "remove %s? ", path);
    else {
        /*
         * If it's not a symbolic link and it's unwritable and we're
         * talking to a terminal, ask.  Symbolic links are excluded
         * because their permissions are meaningless.  Check stdin_ok
         * first because we may not have stat'ed the file.
         */
        if (!stdin_ok || S_ISLNK(sp->st_mode) ||
                (!access(name, W_OK) &&
                 !(sp->st_flags & (SF_APPEND|SF_IMMUTABLE)) &&
                 (!(sp->st_flags & (UF_APPEND|UF_IMMUTABLE)) || !uid)))
            return (1);
        strmode(sp->st_mode, modep);
        if ((flagsp = fflagstostr(sp->st_flags)) == NULL)
            err(1, "fflagstostr");
        if (Pflag)
            errx(1,
                 "%s: -P was specified, but file is not writable",
                 path);
        (void)fprintf(stderr, "override %s%s%s/%s %s%sfor %s? ",
                      modep + 1, modep[9] == ' ' ? "" : " ",
                      user_from_uid(sp->st_uid, 0),
                      group_from_gid(sp->st_gid, 0),
                      *flagsp ? flagsp : "", *flagsp ? " " : "",
                      path);
        free(flagsp);
    }
    (void)fflush(stderr);

    first = ch = getchar();
    while (ch != '\n' && ch != EOF)
        ch = getchar();
    return (first == 'y' || first == 'Y');
}
예제 #5
0
파일: ls.c 프로젝트: AlexZhao/freebsd
/*
 * Display() takes a linked list of FTSENT structures and passes the list
 * along with any other necessary information to the print function.  P
 * points to the parent directory of the display list.
 */
static void
display(const FTSENT *p, FTSENT *list, int options)
{
	struct stat *sp;
	DISPLAY d;
	FTSENT *cur;
	NAMES *np;
	off_t maxsize;
	long maxblock;
	uintmax_t maxinode;
	u_long btotal, labelstrlen, maxlen, maxnlink;
	u_long maxlabelstr;
	u_int sizelen;
	int maxflags;
	gid_t maxgroup;
	uid_t maxuser;
	size_t flen, ulen, glen;
	char *initmax;
	int entries, needstats;
	const char *user, *group;
	char *flags, *labelstr = NULL;
	char ngroup[STRBUF_SIZEOF(uid_t) + 1];
	char nuser[STRBUF_SIZEOF(gid_t) + 1];

	needstats = f_inode || f_longform || f_size;
	flen = 0;
	btotal = 0;
	initmax = getenv("LS_COLWIDTHS");
	/* Fields match -lios order.  New ones should be added at the end. */
	maxlabelstr = maxblock = maxlen = maxnlink = 0;
	maxuser = maxgroup = maxflags = maxsize = 0;
	maxinode = 0;
	if (initmax != NULL && *initmax != '\0') {
		char *initmax2, *jinitmax;
		int ninitmax;

		/* Fill-in "::" as "0:0:0" for the sake of scanf. */
		jinitmax = malloc(strlen(initmax) * 2 + 2);
		if (jinitmax == NULL)
			err(1, "malloc");
		initmax2 = jinitmax;
		if (*initmax == ':')
			strcpy(initmax2, "0:"), initmax2 += 2;
		else
			*initmax2++ = *initmax, *initmax2 = '\0';
		for (initmax++; *initmax != '\0'; initmax++) {
			if (initmax[-1] == ':' && initmax[0] == ':') {
				*initmax2++ = '0';
				*initmax2++ = initmax[0];
				initmax2[1] = '\0';
			} else {
				*initmax2++ = initmax[0];
				initmax2[1] = '\0';
			}
		}
		if (initmax2[-1] == ':')
			strcpy(initmax2, "0");

		ninitmax = sscanf(jinitmax,
		    " %ju : %ld : %lu : %u : %u : %i : %jd : %lu : %lu ",
		    &maxinode, &maxblock, &maxnlink, &maxuser,
		    &maxgroup, &maxflags, &maxsize, &maxlen, &maxlabelstr);
		f_notabs = 1;
		switch (ninitmax) {
		case 0:
			maxinode = 0;
			/* FALLTHROUGH */
		case 1:
			maxblock = 0;
			/* FALLTHROUGH */
		case 2:
			maxnlink = 0;
			/* FALLTHROUGH */
		case 3:
			maxuser = 0;
			/* FALLTHROUGH */
		case 4:
			maxgroup = 0;
			/* FALLTHROUGH */
		case 5:
			maxflags = 0;
			/* FALLTHROUGH */
		case 6:
			maxsize = 0;
			/* FALLTHROUGH */
		case 7:
			maxlen = 0;
			/* FALLTHROUGH */
		case 8:
			maxlabelstr = 0;
			/* FALLTHROUGH */
#ifdef COLORLS
			if (!f_color)
#endif
				f_notabs = 0;
			/* FALLTHROUGH */
		default:
			break;
		}
		MAKENINES(maxinode);
		MAKENINES(maxblock);
		MAKENINES(maxnlink);
		MAKENINES(maxsize);
		free(jinitmax);
	}
	d.s_size = 0;
	sizelen = 0;
	flags = NULL;
	for (cur = list, entries = 0; cur; cur = cur->fts_link) {
		if (cur->fts_info == FTS_ERR || cur->fts_info == FTS_NS) {
			warnx("%s: %s",
			    cur->fts_name, strerror(cur->fts_errno));
			cur->fts_number = NO_PRINT;
			rval = 1;
			continue;
		}
		/*
		 * P is NULL if list is the argv list, to which different rules
		 * apply.
		 */
		if (p == NULL) {
			/* Directories will be displayed later. */
			if (cur->fts_info == FTS_D && !f_listdir) {
				cur->fts_number = NO_PRINT;
				continue;
			}
		} else {
			/* Only display dot file if -a/-A set. */
			if (cur->fts_name[0] == '.' && !f_listdot) {
				cur->fts_number = NO_PRINT;
				continue;
			}
		}
		if (cur->fts_namelen > maxlen)
			maxlen = cur->fts_namelen;
		if (f_octal || f_octal_escape) {
			u_long t = len_octal(cur->fts_name, cur->fts_namelen);

			if (t > maxlen)
				maxlen = t;
		}
		if (needstats) {
			sp = cur->fts_statp;
			if (sp->st_blocks > maxblock)
				maxblock = sp->st_blocks;
			if (sp->st_ino > maxinode)
				maxinode = sp->st_ino;
			if (sp->st_nlink > maxnlink)
				maxnlink = sp->st_nlink;
			if (sp->st_size > maxsize)
				maxsize = sp->st_size;

			btotal += sp->st_blocks;
			if (f_longform) {
				if (f_numericonly) {
					(void)snprintf(nuser, sizeof(nuser),
					    "%u", sp->st_uid);
					(void)snprintf(ngroup, sizeof(ngroup),
					    "%u", sp->st_gid);
					user = nuser;
					group = ngroup;
				} else {
					user = user_from_uid(sp->st_uid, 0);
					group = group_from_gid(sp->st_gid, 0);
				}
				if ((ulen = strlen(user)) > maxuser)
					maxuser = ulen;
				if ((glen = strlen(group)) > maxgroup)
					maxgroup = glen;
				if (f_flags) {
					flags = fflagstostr(sp->st_flags);
					if (flags != NULL && *flags == '\0') {
						free(flags);
						flags = strdup("-");
					}
					if (flags == NULL)
						err(1, "fflagstostr");
					flen = strlen(flags);
					if (flen > (size_t)maxflags)
						maxflags = flen;
				} else
					flen = 0;
				labelstr = NULL;
				if (f_label) {
					char name[PATH_MAX + 1];
					mac_t label;
					int error;

					error = mac_prepare_file_label(&label);
					if (error == -1) {
						warn("MAC label for %s/%s",
						    cur->fts_parent->fts_path,
						    cur->fts_name);
						goto label_out;
					}

					if (cur->fts_level == FTS_ROOTLEVEL)
						snprintf(name, sizeof(name),
						    "%s", cur->fts_name);
					else
						snprintf(name, sizeof(name),
						    "%s/%s", cur->fts_parent->
						    fts_accpath, cur->fts_name);

					if (options & FTS_LOGICAL)
						error = mac_get_file(name,
						    label);
					else
						error = mac_get_link(name,
						    label);
					if (error == -1) {
						warn("MAC label for %s/%s",
						    cur->fts_parent->fts_path,
						    cur->fts_name);
						mac_free(label);
						goto label_out;
					}

					error = mac_to_text(label,
					    &labelstr);
					if (error == -1) {
						warn("MAC label for %s/%s",
						    cur->fts_parent->fts_path,
						    cur->fts_name);
						mac_free(label);
						goto label_out;
					}
					mac_free(label);
label_out:
					if (labelstr == NULL)
						labelstr = strdup("-");
					labelstrlen = strlen(labelstr);
					if (labelstrlen > maxlabelstr)
						maxlabelstr = labelstrlen;
				} else
					labelstrlen = 0;

				if ((np = malloc(sizeof(NAMES) + labelstrlen +
				    ulen + glen + flen + 4)) == NULL)
					err(1, "malloc");

				np->user = &np->data[0];
				(void)strcpy(np->user, user);
				np->group = &np->data[ulen + 1];
				(void)strcpy(np->group, group);

				if (S_ISCHR(sp->st_mode) ||
				    S_ISBLK(sp->st_mode)) {
					sizelen = snprintf(NULL, 0,
					    "%#jx", (uintmax_t)sp->st_rdev);
					if (d.s_size < sizelen)
						d.s_size = sizelen;
				}

				if (f_flags) {
					np->flags = &np->data[ulen + glen + 2];
					(void)strcpy(np->flags, flags);
					free(flags);
				}
				if (f_label) {
					np->label = &np->data[ulen + glen + 2
					    + (f_flags ? flen + 1 : 0)];
					(void)strcpy(np->label, labelstr);
					free(labelstr);
				}
				cur->fts_pointer = np;
			}
		}
		++entries;
	}

	/*
	 * If there are no entries to display, we normally stop right
	 * here.  However, we must continue if we have to display the
	 * total block count.  In this case, we display the total only
	 * on the second (p != NULL) pass.
	 */
	if (!entries && (!(f_longform || f_size) || p == NULL))
		return;

	d.list = list;
	d.entries = entries;
	d.maxlen = maxlen;
	if (needstats) {
		d.btotal = btotal;
		d.s_block = snprintf(NULL, 0, "%lu", howmany(maxblock, blocksize));
		d.s_flags = maxflags;
		d.s_label = maxlabelstr;
		d.s_group = maxgroup;
		d.s_inode = snprintf(NULL, 0, "%ju", maxinode);
		d.s_nlink = snprintf(NULL, 0, "%lu", maxnlink);
		sizelen = f_humanval ? HUMANVALSTR_LEN :
		    snprintf(NULL, 0, "%ju", maxsize);
		if (d.s_size < sizelen)
			d.s_size = sizelen;
		d.s_user = maxuser;
	}
	if (f_thousands)			/* make space for commas */
		d.s_size += (d.s_size - 1) / 3;
	printfcn(&d);
	output = 1;

	if (f_longform)
		for (cur = list; cur; cur = cur->fts_link)
			free(cur->fts_pointer);
}
예제 #6
0
파일: ls.c 프로젝트: aibrahim/OpenBSD-src
/*
 * Display() takes a linked list of FTSENT structures and passes the list
 * along with any other necessary information to the print function.  P
 * points to the parent directory of the display list.
 */
static void
display(FTSENT *p, FTSENT *list)
{
	struct stat *sp;
	DISPLAY d;
	FTSENT *cur;
	NAMES *np;
	off_t maxsize;
	u_long maxlen, maxnlink;
	unsigned long long btotal, maxblock;
	ino_t maxinode;
	int bcfile, flen, glen, ulen, maxflags, maxgroup, maxuser;
	int entries, needstats;
	char *user, *group, buf[21];	/* 64 bits == 20 digits */
	char nuser[12], ngroup[12];
	char *flags = NULL;

	/*
	 * If list is NULL there are two possibilities: that the parent
	 * directory p has no children, or that fts_children() returned an
	 * error.  We ignore the error case since it will be replicated
	 * on the next call to fts_read() on the post-order visit to the
	 * directory p, and will be signalled in traverse().
	 */
	if (list == NULL)
		return;

	needstats = f_inode || f_longform || f_size;
	flen = 0;
	btotal = maxblock = maxinode = maxlen = maxnlink = 0;
	bcfile = 0;
	maxuser = maxgroup = maxflags = 0;
	maxsize = 0;
	for (cur = list, entries = 0; cur != NULL; cur = cur->fts_link) {
		if (cur->fts_info == FTS_ERR || cur->fts_info == FTS_NS) {
			warnx("%s: %s",
			    cur->fts_name, strerror(cur->fts_errno));
			cur->fts_number = NO_PRINT;
			rval = 1;
			continue;
		}

		/*
		 * P is NULL if list is the argv list, to which different rules
		 * apply.
		 */
		if (p == NULL) {
			/* Directories will be displayed later. */
			if (cur->fts_info == FTS_D && !f_listdir) {
				cur->fts_number = NO_PRINT;
				continue;
			}
		} else {
			/* Only display dot file if -a/-A set. */
			if (cur->fts_name[0] == '.' && !f_listdot) {
				cur->fts_number = NO_PRINT;
				continue;
			}
		}
		if (cur->fts_namelen > maxlen)
			maxlen = cur->fts_namelen;
		if (needstats) {
			sp = cur->fts_statp;
			if (sp->st_blocks > maxblock)
				maxblock = sp->st_blocks;
			if (sp->st_ino > maxinode)
				maxinode = sp->st_ino;
			if (sp->st_nlink > maxnlink)
				maxnlink = sp->st_nlink;
			if (sp->st_size > maxsize)
				maxsize = sp->st_size;

			btotal += sp->st_blocks;
			if (f_longform) {
				if (f_numericonly) {
					snprintf(nuser, 12, "%u", sp->st_uid);
					snprintf(ngroup, 12, "%u", sp->st_gid);
					user = nuser;
					group = ngroup;
				} else {
					user = user_from_uid(sp->st_uid, 0);
					group = group_from_gid(sp->st_gid, 0);
				}
				if ((ulen = strlen(user)) > maxuser)
					maxuser = ulen;
				if ((glen = strlen(group)) > maxgroup)
					maxgroup = glen;
				if (f_flags) {
					flags = fflagstostr(sp->st_flags);
					if (*flags == '\0')
						flags = "-";
					if ((flen = strlen(flags)) > maxflags)
						maxflags = flen;
				} else
					flen = 0;

				if ((np = malloc(sizeof(NAMES) +
				    ulen + 1 + glen + 1 + flen + 1)) == NULL)
					err(1, NULL);

				np->user = &np->data[0];
				(void)strlcpy(np->user, user, ulen + 1);
				np->group = &np->data[ulen + 1];
				(void)strlcpy(np->group, group, glen + 1);

				if (S_ISCHR(sp->st_mode) ||
				    S_ISBLK(sp->st_mode))
					bcfile = 1;

				if (f_flags) {
					np->flags = &np->data[ulen + 1 + glen + 1];
				  	(void)strlcpy(np->flags, flags, flen + 1);
					if (*flags != '-')
						free(flags);
				}
				cur->fts_pointer = np;
			}
		}
		++entries;
	}

	if (!entries)
		return;

	d.list = list;
	d.entries = entries;
	d.maxlen = maxlen;
	if (needstats) {
		d.bcfile = bcfile;
		d.btotal = btotal;
		(void)snprintf(buf, sizeof(buf), "%llu", maxblock);
		d.s_block = strlen(buf);
		d.s_flags = maxflags;
		d.s_group = maxgroup;
		(void)snprintf(buf, sizeof(buf), "%llu",
		    (unsigned long long)maxinode);
		d.s_inode = strlen(buf);
		(void)snprintf(buf, sizeof(buf), "%lu", maxnlink);
		d.s_nlink = strlen(buf);
		if (!f_humanval) {
			(void)snprintf(buf, sizeof(buf), "%lld",
				(long long) maxsize);
			d.s_size = strlen(buf);
		} else
			d.s_size = FMT_SCALED_STRSIZE-2; /* no - or '\0' */
		d.s_user = maxuser;
	}

	printfcn(&d);
	output = 1;

	if (f_longform)
		for (cur = list; cur != NULL; cur = cur->fts_link)
			free(cur->fts_pointer);
}
예제 #7
0
파일: create.c 프로젝트: SylvestreG/bitrig
static void
statf(int indent, FTSENT *p)
{
	struct group *gr;
	struct passwd *pw;
	u_int32_t len, val;
	int fd, offset;
	char *name, *escaped_name;
	size_t esc_len;

	esc_len = p->fts_namelen * 4 + 1;
	escaped_name = malloc(esc_len);
	if (escaped_name == NULL)
		error("statf: %s", strerror(errno));
 	strnvis(escaped_name, p->fts_name, esc_len,
	    VIS_WHITE | VIS_OCTAL | VIS_GLOB);

	if (iflag || S_ISDIR(p->fts_statp->st_mode))
		offset = printf("%*s%s", indent, "", escaped_name);
	else
		offset = printf("%*s    %s", indent, "", escaped_name);

	free(escaped_name);

	if (offset > (INDENTNAMELEN + indent))
		offset = MAXLINELEN;
	else
		offset += printf("%*s", (INDENTNAMELEN + indent) - offset, "");

	if (!S_ISREG(p->fts_statp->st_mode) && !dflag)
		output(indent, &offset, "type=%s", inotype(p->fts_statp->st_mode));
	if (p->fts_statp->st_uid != uid) {
		if (keys & F_UNAME) {
			if ((pw = getpwuid(p->fts_statp->st_uid)) != NULL) {
				output(indent, &offset, "uname=%s", pw->pw_name);
			} else {
				error("could not get uname for uid=%u",
				    p->fts_statp->st_uid);
			}
		}
		if (keys & F_UID)
			output(indent, &offset, "uid=%u", p->fts_statp->st_uid);
	}
	if (p->fts_statp->st_gid != gid) {
		if (keys & F_GNAME) {
			if ((gr = getgrgid(p->fts_statp->st_gid)) != NULL) {
				output(indent, &offset, "gname=%s", gr->gr_name);
			} else {
				error("could not get gname for gid=%u",
				    p->fts_statp->st_gid);
			}
		}
		if (keys & F_GID)
			output(indent, &offset, "gid=%u", p->fts_statp->st_gid);
	}
	if (keys & F_MODE && (p->fts_statp->st_mode & MBITS) != mode)
		output(indent, &offset, "mode=%#o", p->fts_statp->st_mode & MBITS);
	if (keys & F_NLINK && p->fts_statp->st_nlink != 1)
		output(indent, &offset, "nlink=%u", p->fts_statp->st_nlink);
	if (keys & F_SIZE && S_ISREG(p->fts_statp->st_mode))
		output(indent, &offset, "size=%qd", p->fts_statp->st_size);
	if (keys & F_TIME)
		output(indent, &offset, "time=%lld.%ld",
		    (long long)p->fts_statp->st_mtimespec.tv_sec,
		    p->fts_statp->st_mtimespec.tv_nsec);
	if (keys & F_CKSUM && S_ISREG(p->fts_statp->st_mode)) {
		if ((fd = open(p->fts_accpath, MTREE_O_FLAGS, 0)) < 0 ||
		    crc(fd, &val, &len))
			error("%s: %s", p->fts_accpath, strerror(errno));
		(void)close(fd);
		output(indent, &offset, "cksum=%u", val);
	}
	if (keys & F_MD5 && S_ISREG(p->fts_statp->st_mode)) {
		char *md5digest, buf[MD5_DIGEST_STRING_LENGTH];

		md5digest = MD5File(p->fts_accpath,buf);
		if (!md5digest)
			error("%s: %s", p->fts_accpath, strerror(errno));
		else
			output(indent, &offset, "md5digest=%s", md5digest);
	}
	if (keys & F_RMD160 && S_ISREG(p->fts_statp->st_mode)) {
		char *rmd160digest, buf[RMD160_DIGEST_STRING_LENGTH];

		rmd160digest = RMD160File(p->fts_accpath,buf);
		if (!rmd160digest)
			error("%s: %s", p->fts_accpath, strerror(errno));
		else
			output(indent, &offset, "rmd160digest=%s", rmd160digest);
	}
	if (keys & F_SHA1 && S_ISREG(p->fts_statp->st_mode)) {
		char *sha1digest, buf[SHA1_DIGEST_STRING_LENGTH];

		sha1digest = SHA1File(p->fts_accpath,buf);
		if (!sha1digest)
			error("%s: %s", p->fts_accpath, strerror(errno));
		else
			output(indent, &offset, "sha1digest=%s", sha1digest);
	}
	if (keys & F_SHA256 && S_ISREG(p->fts_statp->st_mode)) {
		char *sha256digest, buf[SHA256_DIGEST_STRING_LENGTH];

		sha256digest = SHA256File(p->fts_accpath,buf);
		if (!sha256digest)
			error("%s: %s", p->fts_accpath, strerror(errno));
		else
			output(indent, &offset, "sha256digest=%s", sha256digest);
	}
	if (keys & F_SLINK &&
	    (p->fts_info == FTS_SL || p->fts_info == FTS_SLNONE)) {
		name = rlink(p->fts_accpath);
		esc_len = strlen(name) * 4 + 1;
		escaped_name = malloc(esc_len);
		if (escaped_name == NULL)
			error("statf: %s", strerror(errno));
		strnvis(escaped_name, name, esc_len, VIS_WHITE | VIS_OCTAL);
		output(indent, &offset, "link=%s", escaped_name);
		free(escaped_name);
	}
	if (keys & F_FLAGS && !S_ISLNK(p->fts_statp->st_mode)) {
		char *file_flags;

		file_flags = fflagstostr(p->fts_statp->st_flags);
		if (file_flags == NULL)
			error("%s", strerror(errno));
		if (*file_flags != '\0')
			output(indent, &offset, "flags=%s", file_flags);
		else
			output(indent, &offset, "flags=none");
		free(file_flags);
	}
	(void)putchar('\n');
}
예제 #8
0
파일: rm.c 프로젝트: Gwenio/DragonFlyBSD
static int
check(const char *path, const char *name, struct stat *sp)
{
	static int perm_answer = -1;
	struct choice {
		int ch;
		const char *str;
		int res;
		int perm;
	} *choice, choices[] = {
		{ 'y', "yes"   , 1, 0 },
		{ 'n', "no"    , 0, 0 },
		{ 'a', "always", 1, 1 },
		{ 'v', "never" , 0, 1 },
		{ 0, NULL, 0, 0 }
	};
	char modep[15], *flagsp;

	if (perm_answer != -1)
		return (perm_answer);

	/* Check -i first. */
	if (iflag)
		fprintf(stderr, "remove %s? ", path);
	else {
		/*
		 * If it's not a symbolic link and it's unwritable and we're
		 * talking to a terminal, ask.  Symbolic links are excluded
		 * because their permissions are meaningless.  Check stdin_ok
		 * first because we may not have stat'ed the file.
		 * Also skip this check if the -P option was specified because
	         * we will not be able to overwrite file contents and will
	         * barf later.
		 */
		if (!stdin_ok || S_ISLNK(sp->st_mode) || Pflag ||
		    (!access(name, W_OK) &&
		    !(sp->st_flags & (SF_APPEND|SF_IMMUTABLE)) &&
		    (!(sp->st_flags & (UF_APPEND|UF_IMMUTABLE)) || !uid)))
			return (1);
		strmode(sp->st_mode, modep);
		if ((flagsp = fflagstostr(sp->st_flags)) == NULL)
			err(1, NULL);
		fprintf(stderr, "override %s%s%s/%s %s%sfor %s? ",
		    modep + 1, modep[9] == ' ' ? "" : " ",
		    user_from_uid(sp->st_uid, 0),
		    group_from_gid(sp->st_gid, 0),
		    *flagsp ? flagsp : "", *flagsp ? " " : "",
		    path);
		free(flagsp);
	}
	fflush(stderr);

	for (;;) {
		size_t len;
		char *answer;

		answer = fgetln(stdin, &len);
		/* clearerr(stdin); */
		if (answer == NULL)
			return (0);
		if (answer[len - 1] == '\n')
			len--;
		if (len == 0)
			continue;

		for (choice = choices; choice->str != NULL; choice++) {
			if (len == 1 && choice->ch == answer[0])
				goto valid_choice;
			if (strncasecmp(answer, choice->str, len) == 0)
				goto valid_choice;
		}

		fprintf(stderr, "invalid answer, try again (y/n/a/v): ");
	}

valid_choice:
	if (choice->perm)
		perm_answer = choice->res;
	return (choice->res);
}
예제 #9
0
파일: compare.c 프로젝트: ajinkya93/OpenBSD
int
compare(char *name, NODE *s, FTSENT *p)
{
	u_int32_t len, val;
	int fd, label;
	char *cp, *tab = "";

	label = 0;
	switch(s->type) {
	case F_BLOCK:
		if (!S_ISBLK(p->fts_statp->st_mode))
			goto typeerr;
		break;
	case F_CHAR:
		if (!S_ISCHR(p->fts_statp->st_mode))
			goto typeerr;
		break;
	case F_DIR:
		if (!S_ISDIR(p->fts_statp->st_mode))
			goto typeerr;
		break;
	case F_FIFO:
		if (!S_ISFIFO(p->fts_statp->st_mode))
			goto typeerr;
		break;
	case F_FILE:
		if (!S_ISREG(p->fts_statp->st_mode))
			goto typeerr;
		break;
	case F_LINK:
		if (!S_ISLNK(p->fts_statp->st_mode))
			goto typeerr;
		break;
	case F_SOCK:
		if (!S_ISSOCK(p->fts_statp->st_mode)) {
typeerr:		LABEL;
			(void)printf("\ttype (%s, %s)\n",
			    ftype(s->type), inotype(p->fts_statp->st_mode));
		}
		break;
	}
	/* Set the uid/gid first, then set the mode. */
	if (s->flags & (F_UID | F_UNAME) && s->st_uid != p->fts_statp->st_uid) {
		LABEL;
		(void)printf("%suser (%u, %u",
		    tab, s->st_uid, p->fts_statp->st_uid);
		if (uflag)
			if (chown(p->fts_accpath, s->st_uid, -1))
				(void)printf(", not modified: %s)\n",
				    strerror(errno));
			else
				(void)printf(", modified)\n");
		else
			(void)printf(")\n");
		tab = "\t";
	}
	if (s->flags & (F_GID | F_GNAME) && s->st_gid != p->fts_statp->st_gid) {
		LABEL;
		(void)printf("%sgid (%u, %u",
		    tab, s->st_gid, p->fts_statp->st_gid);
		if (uflag)
			if (chown(p->fts_accpath, -1, s->st_gid))
				(void)printf(", not modified: %s)\n",
				    strerror(errno));
			else
				(void)printf(", modified)\n");
		else
			(void)printf(")\n");
		tab = "\t";
	}
	if (s->flags & F_MODE &&
	    s->st_mode != (p->fts_statp->st_mode & MBITS)) {
		if (lflag) {
			mode_t tmode, mode;

			tmode = s->st_mode;
			mode = p->fts_statp->st_mode & MBITS;
			/*
			 * if none of the suid/sgid/etc bits are set,
			 * then if the mode is a subset of the target,
			 * skip.
			 */
			if (!((tmode & ~(S_IRWXU|S_IRWXG|S_IRWXO)) ||
			    (mode & ~(S_IRWXU|S_IRWXG|S_IRWXO))))
				if ((mode | tmode) == tmode)
					goto skip;
		}
		LABEL;
		(void)printf("%spermissions (%#o, %#o",
		    tab, s->st_mode, p->fts_statp->st_mode & MBITS);
		if (uflag)
			if (chmod(p->fts_accpath, s->st_mode))
				(void)printf(", not modified: %s)\n",
				    strerror(errno));
			else
				(void)printf(", modified)\n");
		else
			(void)printf(")\n");
		tab = "\t";
	skip:
		;
	}
	if (s->flags & F_NLINK && s->type != F_DIR &&
	    s->st_nlink != p->fts_statp->st_nlink) {
		LABEL;
		(void)printf("%slink count (%u, %u)\n",
		    tab, s->st_nlink, p->fts_statp->st_nlink);
		tab = "\t";
	}
	if (s->flags & F_SIZE && s->st_size != p->fts_statp->st_size) {
		LABEL;
		(void)printf("%ssize (%qd, %qd)\n",
		    tab, s->st_size, p->fts_statp->st_size);
		tab = "\t";
	}
	/*
	 * XXX
	 * Since utimes(2) only takes a timeval, there's no point in
	 * comparing the low bits of the timespec nanosecond field.  This
	 * will only result in mismatches that we can never fix.
	 *
	 * Doesn't display microsecond differences.
	 */
	if (s->flags & F_TIME) {
		struct timeval tv[2];

		TIMESPEC_TO_TIMEVAL(&tv[0], &s->st_mtimespec);
		TIMESPEC_TO_TIMEVAL(&tv[1], &p->fts_statp->st_mtimespec);
		if (tv[0].tv_sec != tv[1].tv_sec ||
		    tv[0].tv_usec != tv[1].tv_usec) {
			LABEL;
			(void)printf("%smodification time (%.24s, ",
			    tab, ctime(&s->st_mtimespec.tv_sec));
			(void)printf("%.24s",
			    ctime(&p->fts_statp->st_mtimespec.tv_sec));
			if (tflag) {
				tv[1] = tv[0];
				if (utimes(p->fts_accpath, tv))
					(void)printf(", not modified: %s)\n",
					    strerror(errno));
				else  
					(void)printf(", modified)\n");  
			} else
				(void)printf(")\n");
			tab = "\t";   
		}
	}
	if (s->flags & F_CKSUM) {
		if ((fd = open(p->fts_accpath, MTREE_O_FLAGS, 0)) < 0) {
			LABEL;
			(void)printf("%scksum: %s: %s\n",
			    tab, p->fts_accpath, strerror(errno));
			tab = "\t";
		} else if (crc(fd, &val, &len)) {
			(void)close(fd);
			LABEL;
			(void)printf("%scksum: %s: %s\n",
			    tab, p->fts_accpath, strerror(errno));
			tab = "\t";
		} else {
			(void)close(fd);
			if (s->cksum != val) {
				LABEL;
				(void)printf("%scksum (%u, %u)\n",
				    tab, s->cksum, val);
			}
			tab = "\t";
		}
	}
	if (s->flags & F_MD5) {
		char *new_digest, buf[MD5_DIGEST_STRING_LENGTH];

		new_digest = MD5File(p->fts_accpath, buf);
		if (!new_digest) {
			LABEL;
			printf("%sMD5File: %s: %s\n", tab, p->fts_accpath,
			       strerror(errno));
			tab = "\t";
		} else if (strcmp(new_digest, s->md5digest)) {
			LABEL;
			printf("%sMD5 (%s, %s)\n", tab, s->md5digest,
			       new_digest);
			tab = "\t";
		}
	}
	if (s->flags & F_RMD160) {
		char *new_digest, buf[RMD160_DIGEST_STRING_LENGTH];

		new_digest = RMD160File(p->fts_accpath, buf);
		if (!new_digest) {
			LABEL;
			printf("%sRMD160File: %s: %s\n", tab, p->fts_accpath,
			       strerror(errno));
			tab = "\t";
		} else if (strcmp(new_digest, s->rmd160digest)) {
			LABEL;
			printf("%sRMD160 (%s, %s)\n", tab, s->rmd160digest,
			       new_digest);
			tab = "\t";
		}
	}
	if (s->flags & F_SHA1) {
		char *new_digest, buf[SHA1_DIGEST_STRING_LENGTH];

		new_digest = SHA1File(p->fts_accpath, buf);
		if (!new_digest) {
			LABEL;
			printf("%sSHA1File: %s: %s\n", tab, p->fts_accpath,
			       strerror(errno));
			tab = "\t";
		} else if (strcmp(new_digest, s->sha1digest)) {
			LABEL;
			printf("%sSHA1 (%s, %s)\n", tab, s->sha1digest,
			       new_digest);
			tab = "\t";
		}
	}
	if (s->flags & F_SHA256) {
		char *new_digest, buf[SHA256_DIGEST_STRING_LENGTH];

		new_digest = SHA256File(p->fts_accpath, buf);
		if (!new_digest) {
			LABEL;
			printf("%sSHA256File: %s: %s\n", tab, p->fts_accpath,
			       strerror(errno));
			tab = "\t";
		} else if (strcmp(new_digest, s->sha256digest)) {
			LABEL;
			printf("%sSHA256 (%s, %s)\n", tab, s->sha256digest,
			       new_digest);
			tab = "\t";
		}
	}
	if (s->flags & F_SLINK && strcmp(cp = rlink(name), s->slink)) {
		LABEL;
		(void)printf("%slink ref (%s, %s)\n", tab, cp, s->slink);
	}
	if (s->flags & F_FLAGS && s->file_flags != p->fts_statp->st_flags) {
		char *db_flags = NULL;
		char *cur_flags = NULL;

		if ((db_flags = fflagstostr(s->file_flags)) == NULL ||
		    (cur_flags = fflagstostr(p->fts_statp->st_flags)) == NULL) {
			LABEL;
			(void)printf("%sflags: %s %s\n", tab, p->fts_accpath,
				     strerror(errno));
			tab = "\t";
			free(db_flags);
			free(cur_flags);
		} else {
			LABEL;
			REPLACE_COMMA(db_flags);
			REPLACE_COMMA(cur_flags);
			printf("%sflags (%s, %s", tab, (*db_flags == '\0') ?
						  "-" : db_flags,
						  (*cur_flags == '\0') ? 
						  "-" : cur_flags);
				tab = "\t";
			if (uflag)
				if (chflags(p->fts_accpath, s->file_flags))
					(void)printf(", not modified: %s)\n",
						strerror(errno));
				else	
					(void)printf(", modified)\n");
			else
				(void)printf(")\n");
			tab = "\t"; 

			free(db_flags);
			free(cur_flags);
		}
	}
	return (label);
}