/* vi: set sw=4 ts=4: */
/*
 * chattr.c		- Change file attributes on an ext2 file system
 *
 * Copyright (C) 1993, 1994  Remy Card <card@masi.ibp.fr>
 *                           Laboratoire MASI, Institut Blaise Pascal
 *                           Universite Pierre et Marie Curie (Paris VI)
 *
 * This file can be redistributed under the terms of the GNU General
 * Public License
 */

/*
 * History:
 * 93/10/30	- Creation
 * 93/11/13	- Replace stat() calls by lstat() to avoid loops
 * 94/02/27	- Integrated in Ted's distribution
 * 98/12/29	- Ignore symlinks when working recursively (G M Sipe)
 * 98/12/29	- Display version info only when -V specified (G M Sipe)
 */

#include "busybox.h"
#include "e2fs_lib.h"

#define OPT_ADD 1
#define OPT_REM 2
#define OPT_SET 4
#define OPT_SET_VER 8
static int flags;
static int recursive;

static unsigned long version;

static unsigned long af;
static unsigned long rf;
static unsigned long sf;

struct flags_char {
	unsigned long flag;
	char optchar;
};

static const struct flags_char flags_array[] = {
	{ EXT2_NOATIME_FL,      'A' },
	{ EXT2_SYNC_FL,         'S' },
	{ EXT2_DIRSYNC_FL,      'D' },
	{ EXT2_APPEND_FL,       'a' },
	{ EXT2_COMPR_FL,        'c' },
	{ EXT2_NODUMP_FL,       'd' },
	{ EXT2_IMMUTABLE_FL,    'i' },
	{ EXT3_JOURNAL_DATA_FL, 'j' },
	{ EXT2_SECRM_FL,        's' },
	{ EXT2_UNRM_FL,         'u' },
	{ EXT2_NOTAIL_FL,       't' },
	{ EXT2_TOPDIR_FL,       'T' },
	{ 0, 0 }
};

static unsigned long get_flag(char c)
{
	const struct flags_char *fp;
	for (fp = flags_array; fp->optchar; fp++)
		if (fp->optchar == c)
			return fp->flag;
	bb_show_usage();
}

static int decode_arg(const char *arg)
{
	unsigned long *fl;
	char opt = *arg++;

	if (opt == '-') {
		flags |= OPT_REM;
		fl = &rf;
	} else if (opt == '+') {
		flags |= OPT_ADD;
		fl = &af;
	} else if (opt == '=') {
		flags |= OPT_SET;
		fl = &sf;
	} else
		return 0;

	while (*arg)
		*fl |= get_flag(*arg++);

	return 1;
}

static void change_attributes(const char *name);

static int chattr_dir_proc(const char *dir_name, struct dirent *de,
			void *private ATTRIBUTE_UNUSED)
{
	char *path = concat_subpath_file(dir_name, de->d_name);
	/* path is NULL if de->d_name is "." or "..", else... */
	if (path) {
		change_attributes(path);
		free(path);
	}
	return 0;
}

static void change_attributes(const char *name)
{
	unsigned long fsflags;
	struct stat st;

	if (lstat(name, &st) == -1) {
		bb_perror_msg("stat %s", name);
		return;
	}
	if (S_ISLNK(st.st_mode) && recursive)
		return;

	/* Don't try to open device files, fifos etc.  We probably
	 * ought to display an error if the file was explicitly given
	 * on the command line (whether or not recursive was
	 * requested).  */
	if (!S_ISREG(st.st_mode) && !S_ISLNK(st.st_mode) && !S_ISDIR(st.st_mode))
		return;

	if (flags & OPT_SET_VER)
		if (fsetversion(name, version) == -1)
			bb_perror_msg("setting version on %s", name);

	if (flags & OPT_SET) {
		fsflags = sf;
	} else {
		if (fgetflags(name, &fsflags) == -1) {
			bb_perror_msg("reading flags on %s", name);
			goto skip_setflags;
		}
		if (flags & OPT_REM)
			fsflags &= ~rf;
		if (flags & OPT_ADD)
			fsflags |= af;
		if (!S_ISDIR(st.st_mode))
			fsflags &= ~EXT2_DIRSYNC_FL;
	}
	if (fsetflags(name, fsflags) == -1)
		bb_perror_msg("setting flags on %s", name);

 skip_setflags:
	if (recursive && S_ISDIR(st.st_mode))
		iterate_on_dir(name, chattr_dir_proc, NULL);
}

int chattr_main(int argc, char **argv)
{
	char *arg;

	/* parse the args */
	while ((arg = *++argv)) {
		/* take care of -R and -v <version> */
		if (arg[0] == '-') {
			if (arg[1] == 'R' && arg[2] == '\0') {
				recursive = 1;
				continue;
			}
			if (arg[1] == 'v' && arg[2] == '\0') {
				if (!*++argv)
					bb_show_usage();
				version = xatoul(*argv);
				flags |= OPT_SET_VER;
				continue;
			}
		}

		if (!decode_arg(arg))
			break;
	}

	/* run sanity checks on all the arguments given us */
	if (!*argv)
		bb_show_usage();
	if ((flags & OPT_SET) && (flags & (OPT_ADD|OPT_REM)))
		bb_error_msg_and_die("= is incompatible with - and +");
	if (rf & af)
		bb_error_msg_and_die("can't set and unset a flag");
	if (!flags)
		bb_error_msg_and_die("must use '-v', =, - or +");

	/* now run chattr on all the files passed to us */
	do change_attributes(*argv); while (*++argv);

	return EXIT_SUCCESS;
}
