Exemple #1
0
/**
 * acct_auto_close - turn off a filesystem's accounting if it is on
 * @m: vfsmount being shut down
 *
 * If the accounting is turned on for a file in the subtree pointed to
 * to by m, turn accounting off.  Done when m is about to die.
 */
void acct_auto_close_mnt(struct vfsmount *m)
{
	spin_lock(&acct_globals.lock);
	if (acct_globals.file && acct_globals.file->f_path.mnt == m)
		acct_file_reopen(NULL);
	spin_unlock(&acct_globals.lock);
}
Exemple #2
0
/**
 * sys_acct - enable/disable process accounting
 * @name: file name for accounting records or NULL to shutdown accounting
 *
 * Returns 0 for success or negative errno values for failure.
 *
 * sys_acct() is the only system call needed to implement process
 * accounting. It takes the name of the file where accounting records
 * should be written. If the filename is NULL, accounting will be
 * shutdown.
 */
SYSCALL_DEFINE1(acct, const char __user *, name)
{
	int error;

	if (!capable(CAP_SYS_PACCT))
		return -EPERM;

	if (name) {
		char *tmp = getname(name);
		if (IS_ERR(tmp))
			return (PTR_ERR(tmp));
		error = acct_on(tmp);
		putname(tmp);
	} else {
		struct bsd_acct_struct *acct;

		acct = task_active_pid_ns(current)->bacct;
		if (acct == NULL)
			return 0;

		error = security_acct(NULL);
		if (!error) {
			spin_lock(&acct_lock);
			acct_file_reopen(acct, NULL, NULL);
			spin_unlock(&acct_lock);
		}
	}
	return error;
}
Exemple #3
0
static int acct_on(char *name)
{
	struct file *file;
	int error;

	/* Difference from BSD - they don't do O_APPEND */
	file = filp_open(name, O_WRONLY|O_APPEND|O_LARGEFILE, 0);
	if (IS_ERR(file))
		return PTR_ERR(file);

	if (!S_ISREG(file->f_path.dentry->d_inode->i_mode)) {
		filp_close(file, NULL);
		return -EACCES;
	}

	if (!file->f_op->write) {
		filp_close(file, NULL);
		return -EIO;
	}

	error = security_acct(file);
	if (error) {
		filp_close(file, NULL);
		return error;
	}

	spin_lock(&acct_globals.lock);
	mnt_pin(file->f_path.mnt);
	acct_file_reopen(file);
	spin_unlock(&acct_globals.lock);

	mntput(file->f_path.mnt); /* it's pinned, now give up active reference */

	return 0;
}
Exemple #4
0
/*
 * If the accouting is turned on for a file in the filesystem pointed
 * to by sb, turn accouting off.
 */
void acct_auto_close(struct super_block *sb)
{
	spin_lock(&acct_globals.lock);
	if (acct_globals.file &&
	    acct_globals.file->f_dentry->d_inode->i_sb == sb) {
		acct_file_reopen((struct file *)NULL);
	}
	spin_unlock(&acct_globals.lock);
}
Exemple #5
0
/**
 * acct_auto_close - turn off a filesystem's accounting if it is on
 * @sb: super block for the filesystem
 *
 * If the accounting is turned on for a file in the filesystem pointed
 * to by sb, turn accounting off.
 */
void acct_auto_close(struct super_block *sb)
{
	spin_lock(&acct_globals.lock);
	if (acct_globals.file &&
	    acct_globals.file->f_path.mnt->mnt_sb == sb) {
		acct_file_reopen(NULL);
	}
	spin_unlock(&acct_globals.lock);
}
Exemple #6
0
static int acct_on(char *name)
{
	struct file *file;
	struct vfsmount *mnt;
	int error;
	struct pid_namespace *ns;
	struct bsd_acct_struct *acct = NULL;

	/* Difference from BSD - they don't do O_APPEND */
	file = filp_open(name, O_WRONLY|O_APPEND|O_LARGEFILE, 0);
	if (IS_ERR(file))
		return PTR_ERR(file);

	if (!S_ISREG(file->f_path.dentry->d_inode->i_mode)) {
		filp_close(file, NULL);
		return -EACCES;
	}

	if (!file->f_op->write) {
		filp_close(file, NULL);
		return -EIO;
	}

	ns = task_active_pid_ns(current);
	if (ns->bacct == NULL) {
		acct = kzalloc(sizeof(struct bsd_acct_struct), GFP_KERNEL);
		if (acct == NULL) {
			filp_close(file, NULL);
			return -ENOMEM;
		}
	}

	error = security_acct(file);
	if (error) {
		kfree(acct);
		filp_close(file, NULL);
		return error;
	}

	spin_lock(&acct_lock);
	if (ns->bacct == NULL) {
		ns->bacct = acct;
		acct = NULL;
	}

	mnt = file->f_path.mnt;
	mnt_pin(mnt);
	acct_file_reopen(ns->bacct, file, ns);
	spin_unlock(&acct_lock);

	mntput(mnt); /* it's pinned, now give up active reference */
	kfree(acct);

	return 0;
}
Exemple #7
0
/**
 * acct_auto_close - turn off a filesystem's accounting if it is on
 * @sb: super block for the filesystem
 *
 * If the accounting is turned on for a file in the filesystem pointed
 * to by sb, turn accounting off.
 */
void acct_auto_close(struct super_block *sb)
{
	struct bsd_acct_struct *acct;

	spin_lock(&acct_lock);
restart:
	list_for_each_entry(acct, &acct_list, list)
		if (acct->file && acct->file->f_path.mnt->mnt_sb == sb) {
			acct_file_reopen(acct, NULL, NULL);
			goto restart;
		}
	spin_unlock(&acct_lock);
}
Exemple #8
0
/**
 * acct_auto_close - turn off a filesystem's accounting if it is on
 * @m: vfsmount being shut down
 *
 * If the accounting is turned on for a file in the subtree pointed to
 * to by m, turn accounting off.  Done when m is about to die.
 */
void acct_auto_close_mnt(struct vfsmount *m)
{
	struct bsd_acct_struct *acct;

	spin_lock(&acct_lock);
restart:
	list_for_each_entry(acct, &acct_list, list)
		if (acct->file && acct->file->f_path.mnt == m) {
			acct_file_reopen(acct, NULL, NULL);
			goto restart;
		}
	spin_unlock(&acct_lock);
}
Exemple #9
0
void acct_exit_ns(struct pid_namespace *ns)
{
	struct bsd_acct_struct *acct;

	spin_lock(&acct_lock);
	acct = ns->bacct;
	if (acct != NULL) {
		if (acct->file != NULL)
			acct_file_reopen(acct, NULL, NULL);

		kfree(acct);
	}
	spin_unlock(&acct_lock);
}
Exemple #10
0
void acct_exit_ns(struct pid_namespace *ns)
{
	struct bsd_acct_struct *acct = ns->bacct;

	if (acct == NULL)
		return;

	del_timer_sync(&acct->timer);
	spin_lock(&acct_lock);
	if (acct->file != NULL)
		acct_file_reopen(acct, NULL, NULL);
	spin_unlock(&acct_lock);

	kfree(acct);
}
Exemple #11
0
/*
 *  sys_acct() is the only system call needed to implement process
 *  accounting. It takes the name of the file where accounting records
 *  should be written. If the filename is NULL, accounting will be
 *  shutdown.
 */
asmlinkage long sys_acct(const char __user *name)
{
	struct file *file = NULL;
	char *tmp;
	int error;

	if (!capable(CAP_SYS_PACCT))
		return -EPERM;

	if (name) {
		tmp = getname(name);
		if (IS_ERR(tmp)) {
			return (PTR_ERR(tmp));
		}
		/* Difference from BSD - they don't do O_APPEND */
		file = filp_open(tmp, O_WRONLY|O_APPEND, 0);
		putname(tmp);
		if (IS_ERR(file)) {
			return (PTR_ERR(file));
		}
		if (!S_ISREG(file->f_dentry->d_inode->i_mode)) {
			filp_close(file, NULL);
			return (-EACCES);
		}

		if (!file->f_op->write) {
			filp_close(file, NULL);
			return (-EIO);
		}
	}

	error = security_acct(file);
	if (error) {
		if (file)
			filp_close(file, NULL);
		return error;
	}

	spin_lock(&acct_globals.lock);
	acct_file_reopen(file);
	spin_unlock(&acct_globals.lock);

	return (0);
}
Exemple #12
0
/**
 * sys_acct - enable/disable process accounting
 * @name: file name for accounting records or NULL to shutdown accounting
 *
 * Returns 0 for success or negative errno values for failure.
 *
 * sys_acct() is the only system call needed to implement process
 * accounting. It takes the name of the file where accounting records
 * should be written. If the filename is NULL, accounting will be
 * shutdown.
 */
asmlinkage long sys_acct(const char __user *name)
{
	int error;

	if (!capable(CAP_SYS_PACCT))
		return -EPERM;

	if (name) {
		char *tmp = getname(name);
		if (IS_ERR(tmp))
			return (PTR_ERR(tmp));
		error = acct_on(tmp);
		putname(tmp);
	} else {
		error = security_acct(NULL);
		if (!error) {
			spin_lock(&acct_globals.lock);
			acct_file_reopen(NULL);
			spin_unlock(&acct_globals.lock);
		}
	}
	return error;
}