devtmpfs.c revision 1ac12b4b6d707937f9de6d09622823b2fd0c93ef
12b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers/*
22b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers * devtmpfs - kernel-maintained tmpfs-based /dev
32b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers *
42b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers * Copyright (C) 2009, Kay Sievers <kay.sievers@vrfy.org>
52b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers *
62b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers * During bootup, before any driver core device is registered,
72b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers * devtmpfs, a tmpfs-based filesystem is created. Every driver-core
82b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers * device which requests a device node, will add a node in this
9e454cea20bdcff10ee698d11b8882662a0153a47Kay Sievers * filesystem.
1002fbe5e61df654b2b39a1ddc1ae912c9e14c3dddPeter Korsgaard * By default, all devices are named after the name of the device,
1102fbe5e61df654b2b39a1ddc1ae912c9e14c3dddPeter Korsgaard * owned by root and have a default mode of 0600. Subsystems can
1202fbe5e61df654b2b39a1ddc1ae912c9e14c3dddPeter Korsgaard * overwrite the default setting if needed.
132b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers */
142b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
152b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers#include <linux/kernel.h>
162b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers#include <linux/syscalls.h>
172b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers#include <linux/mount.h>
182b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers#include <linux/device.h>
192b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers#include <linux/genhd.h>
202b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers#include <linux/namei.h>
212b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers#include <linux/fs.h>
222b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers#include <linux/shmem_fs.h>
23da5e4ef7fdb8f2fb0878dee3bd9d4dd10cea8cf1Peter Korsgaard#include <linux/ramfs.h>
24e454cea20bdcff10ee698d11b8882662a0153a47Kay Sievers#include <linux/sched.h>
255a0e3ad6af8660be21ca98a971cd00f331318c05Tejun Heo#include <linux/slab.h>
262780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro#include <linux/kthread.h>
272b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
282780f1ff6aec0cf708a61c022d475bfcaa648965Al Virostatic struct task_struct *thread;
292b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
302b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers#if defined CONFIG_DEVTMPFS_MOUNT
31fc14f2fef682df677d64a145256dbd263df2aa7bAl Virostatic int mount_dev = 1;
322b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers#else
33fc14f2fef682df677d64a145256dbd263df2aa7bAl Virostatic int mount_dev;
342b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers#endif
352b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
362780f1ff6aec0cf708a61c022d475bfcaa648965Al Virostatic DEFINE_SPINLOCK(req_lock);
372780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
382780f1ff6aec0cf708a61c022d475bfcaa648965Al Virostatic struct req {
392780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	struct req *next;
402780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	struct completion done;
412780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	int err;
422780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	const char *name;
432c9ede55ecec58099b72e4bb8eab719f32f72c31Al Viro	umode_t mode;	/* 0 => delete */
442780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	struct device *dev;
452780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro} *requests;
46ed413ae6e7813d3227eef43bc6d84ca4f4fe6b21Kay Sievers
472b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sieversstatic int __init mount_param(char *str)
482b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers{
49fc14f2fef682df677d64a145256dbd263df2aa7bAl Viro	mount_dev = simple_strtoul(str, NULL, 0);
502b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	return 1;
512b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers}
522b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers__setup("devtmpfs.mount=", mount_param);
532b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
54fc14f2fef682df677d64a145256dbd263df2aa7bAl Virostatic struct dentry *dev_mount(struct file_system_type *fs_type, int flags,
55fc14f2fef682df677d64a145256dbd263df2aa7bAl Viro		      const char *dev_name, void *data)
562b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers{
57da5e4ef7fdb8f2fb0878dee3bd9d4dd10cea8cf1Peter Korsgaard#ifdef CONFIG_TMPFS
58fc14f2fef682df677d64a145256dbd263df2aa7bAl Viro	return mount_single(fs_type, flags, data, shmem_fill_super);
59da5e4ef7fdb8f2fb0878dee3bd9d4dd10cea8cf1Peter Korsgaard#else
60fc14f2fef682df677d64a145256dbd263df2aa7bAl Viro	return mount_single(fs_type, flags, data, ramfs_fill_super);
61da5e4ef7fdb8f2fb0878dee3bd9d4dd10cea8cf1Peter Korsgaard#endif
622b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers}
632b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
642b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sieversstatic struct file_system_type dev_fs_type = {
652b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	.name = "devtmpfs",
66fc14f2fef682df677d64a145256dbd263df2aa7bAl Viro	.mount = dev_mount,
672b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	.kill_sb = kill_litter_super,
682b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers};
692b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
702b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers#ifdef CONFIG_BLOCK
712b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sieversstatic inline int is_blockdev(struct device *dev)
722b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers{
732b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	return dev->class == &block_class;
742b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers}
752b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers#else
762b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sieversstatic inline int is_blockdev(struct device *dev) { return 0; }
772b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers#endif
782b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
792780f1ff6aec0cf708a61c022d475bfcaa648965Al Viroint devtmpfs_create_node(struct device *dev)
802780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro{
812780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	const char *tmp = NULL;
822780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	struct req req;
832780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
842780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	if (!thread)
852780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro		return 0;
862780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
872780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	req.mode = 0;
882780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	req.name = device_get_devnode(dev, &req.mode, &tmp);
892780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	if (!req.name)
902780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro		return -ENOMEM;
912780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
922780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	if (req.mode == 0)
932780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro		req.mode = 0600;
942780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	if (is_blockdev(dev))
952780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro		req.mode |= S_IFBLK;
962780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	else
972780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro		req.mode |= S_IFCHR;
982780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
992780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	req.dev = dev;
1002780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
1012780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	init_completion(&req.done);
1022780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
1032780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	spin_lock(&req_lock);
1042780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	req.next = requests;
1052780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	requests = &req;
1062780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	spin_unlock(&req_lock);
1072780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
1082780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	wake_up_process(thread);
1092780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	wait_for_completion(&req.done);
1102780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
1112780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	kfree(tmp);
1122780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
1132780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	return req.err;
1142780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro}
1152780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
1162780f1ff6aec0cf708a61c022d475bfcaa648965Al Viroint devtmpfs_delete_node(struct device *dev)
1172780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro{
1182780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	const char *tmp = NULL;
1192780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	struct req req;
1202780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
1212780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	if (!thread)
1222780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro		return 0;
1232780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
1242780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	req.name = device_get_devnode(dev, NULL, &tmp);
1252780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	if (!req.name)
1262780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro		return -ENOMEM;
1272780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
1282780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	req.mode = 0;
1292780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	req.dev = dev;
1302780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
1312780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	init_completion(&req.done);
1322780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
1332780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	spin_lock(&req_lock);
1342780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	req.next = requests;
1352780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	requests = &req;
1362780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	spin_unlock(&req_lock);
1372780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
1382780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	wake_up_process(thread);
1392780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	wait_for_completion(&req.done);
1402780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
1412780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	kfree(tmp);
1422780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	return req.err;
1432780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro}
1442780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
145fbd48a69a0b576dd8cba01b2b4fc24fad76f1b68Al Virostatic int dev_mkdir(const char *name, umode_t mode)
1462b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers{
1472b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	struct dentry *dentry;
14869753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro	struct path path;
1492b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	int err;
1502b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
1511ac12b4b6d707937f9de6d09622823b2fd0c93efJeff Layton	dentry = kern_path_create(AT_FDCWD, name, &path, LOOKUP_DIRECTORY);
15269753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro	if (IS_ERR(dentry))
15369753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro		return PTR_ERR(dentry);
15469753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro
15569753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro	err = vfs_mkdir(path.dentry->d_inode, dentry, mode);
15669753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro	if (!err)
15769753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro		/* mark as kernel-created inode */
15869753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro		dentry->d_inode->i_private = &thread;
159921a1650de9eed40dd64d681aba4a4d98856f289Al Viro	done_path_create(&path, dentry);
1602b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	return err;
1612b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers}
1622b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
1632b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sieversstatic int create_path(const char *nodepath)
1642b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers{
1655da4e689449ad99ab31cf2208d99eddfce0498baAl Viro	char *path;
1665da4e689449ad99ab31cf2208d99eddfce0498baAl Viro	char *s;
1679d108d25487bf958f8093409a4c0bee6169edba6Al Viro	int err = 0;
1682b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
1695da4e689449ad99ab31cf2208d99eddfce0498baAl Viro	/* parent directories do not exist, create them */
1705da4e689449ad99ab31cf2208d99eddfce0498baAl Viro	path = kstrdup(nodepath, GFP_KERNEL);
1715da4e689449ad99ab31cf2208d99eddfce0498baAl Viro	if (!path)
1725da4e689449ad99ab31cf2208d99eddfce0498baAl Viro		return -ENOMEM;
1735da4e689449ad99ab31cf2208d99eddfce0498baAl Viro
1745da4e689449ad99ab31cf2208d99eddfce0498baAl Viro	s = path;
1755da4e689449ad99ab31cf2208d99eddfce0498baAl Viro	for (;;) {
1765da4e689449ad99ab31cf2208d99eddfce0498baAl Viro		s = strchr(s, '/');
1775da4e689449ad99ab31cf2208d99eddfce0498baAl Viro		if (!s)
1785da4e689449ad99ab31cf2208d99eddfce0498baAl Viro			break;
1795da4e689449ad99ab31cf2208d99eddfce0498baAl Viro		s[0] = '\0';
1805da4e689449ad99ab31cf2208d99eddfce0498baAl Viro		err = dev_mkdir(path, 0755);
1815da4e689449ad99ab31cf2208d99eddfce0498baAl Viro		if (err && err != -EEXIST)
1825da4e689449ad99ab31cf2208d99eddfce0498baAl Viro			break;
1835da4e689449ad99ab31cf2208d99eddfce0498baAl Viro		s[0] = '/';
1845da4e689449ad99ab31cf2208d99eddfce0498baAl Viro		s++;
1852b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	}
1865da4e689449ad99ab31cf2208d99eddfce0498baAl Viro	kfree(path);
1872b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	return err;
1882b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers}
1892b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
190fbd48a69a0b576dd8cba01b2b4fc24fad76f1b68Al Virostatic int handle_create(const char *nodename, umode_t mode, struct device *dev)
1912b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers{
1922b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	struct dentry *dentry;
19369753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro	struct path path;
1942b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	int err;
1952b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
19669753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro	dentry = kern_path_create(AT_FDCWD, nodename, &path, 0);
19769753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro	if (dentry == ERR_PTR(-ENOENT)) {
1982b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		create_path(nodename);
19969753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro		dentry = kern_path_create(AT_FDCWD, nodename, &path, 0);
2002b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	}
20169753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro	if (IS_ERR(dentry))
20269753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro		return PTR_ERR(dentry);
20369753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro
20469753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro	err = vfs_mknod(path.dentry->d_inode,
20569753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro			dentry, mode, dev->devt);
20669753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro	if (!err) {
20769753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro		struct iattr newattrs;
20869753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro
20969753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro		/* fixup possibly umasked mode */
21069753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro		newattrs.ia_mode = mode;
21169753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro		newattrs.ia_valid = ATTR_MODE;
21269753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro		mutex_lock(&dentry->d_inode->i_mutex);
21369753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro		notify_change(dentry, &newattrs);
21469753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro		mutex_unlock(&dentry->d_inode->i_mutex);
21569753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro
21669753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro		/* mark as kernel-created inode */
21769753a0f14d3cb2e8a70e559ef8d409e4deeac8aAl Viro		dentry->d_inode->i_private = &thread;
2182b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	}
219921a1650de9eed40dd64d681aba4a4d98856f289Al Viro	done_path_create(&path, dentry);
2202b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	return err;
2212b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers}
2222b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
2232b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sieversstatic int dev_rmdir(const char *name)
2242b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers{
22579714f72d3b964611997de512cb29198c9f2dbbbAl Viro	struct path parent;
2262b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	struct dentry *dentry;
2272b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	int err;
2282b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
22979714f72d3b964611997de512cb29198c9f2dbbbAl Viro	dentry = kern_path_locked(name, &parent);
23079714f72d3b964611997de512cb29198c9f2dbbbAl Viro	if (IS_ERR(dentry))
23179714f72d3b964611997de512cb29198c9f2dbbbAl Viro		return PTR_ERR(dentry);
23279714f72d3b964611997de512cb29198c9f2dbbbAl Viro	if (dentry->d_inode) {
23379714f72d3b964611997de512cb29198c9f2dbbbAl Viro		if (dentry->d_inode->i_private == &thread)
23479714f72d3b964611997de512cb29198c9f2dbbbAl Viro			err = vfs_rmdir(parent.dentry->d_inode, dentry);
23579714f72d3b964611997de512cb29198c9f2dbbbAl Viro		else
23679714f72d3b964611997de512cb29198c9f2dbbbAl Viro			err = -EPERM;
2372b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	} else {
23879714f72d3b964611997de512cb29198c9f2dbbbAl Viro		err = -ENOENT;
2392b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	}
24079714f72d3b964611997de512cb29198c9f2dbbbAl Viro	dput(dentry);
24179714f72d3b964611997de512cb29198c9f2dbbbAl Viro	mutex_unlock(&parent.dentry->d_inode->i_mutex);
24279714f72d3b964611997de512cb29198c9f2dbbbAl Viro	path_put(&parent);
2432b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	return err;
2442b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers}
2452b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
2462b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sieversstatic int delete_path(const char *nodepath)
2472b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers{
2482b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	const char *path;
2492b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	int err = 0;
2502b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
2512b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	path = kstrdup(nodepath, GFP_KERNEL);
2522b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	if (!path)
2532b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		return -ENOMEM;
2542b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
255ed413ae6e7813d3227eef43bc6d84ca4f4fe6b21Kay Sievers	for (;;) {
2562b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		char *base;
2572b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
2582b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		base = strrchr(path, '/');
2592b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		if (!base)
2602b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers			break;
2612b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		base[0] = '\0';
2622b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		err = dev_rmdir(path);
2632b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		if (err)
2642b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers			break;
2652b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	}
2662b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
2672b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	kfree(path);
2682b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	return err;
2692b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers}
2702b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
2712b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sieversstatic int dev_mynode(struct device *dev, struct inode *inode, struct kstat *stat)
2722b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers{
2732b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	/* did we create it */
2742780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	if (inode->i_private != &thread)
2752b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		return 0;
2762b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
2772b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	/* does the dev_t match */
2782b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	if (is_blockdev(dev)) {
2792b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		if (!S_ISBLK(stat->mode))
2802b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers			return 0;
2812b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	} else {
2822b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		if (!S_ISCHR(stat->mode))
2832b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers			return 0;
2842b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	}
2852b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	if (stat->rdev != dev->devt)
2862b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		return 0;
2872b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
2882b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	/* ours */
2892b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	return 1;
2902b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers}
2912b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
2922780f1ff6aec0cf708a61c022d475bfcaa648965Al Virostatic int handle_remove(const char *nodename, struct device *dev)
2932b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers{
29479714f72d3b964611997de512cb29198c9f2dbbbAl Viro	struct path parent;
2952b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	struct dentry *dentry;
2962b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	int deleted = 1;
2972b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	int err;
2982b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
29979714f72d3b964611997de512cb29198c9f2dbbbAl Viro	dentry = kern_path_locked(nodename, &parent);
30079714f72d3b964611997de512cb29198c9f2dbbbAl Viro	if (IS_ERR(dentry))
30179714f72d3b964611997de512cb29198c9f2dbbbAl Viro		return PTR_ERR(dentry);
30279714f72d3b964611997de512cb29198c9f2dbbbAl Viro
30379714f72d3b964611997de512cb29198c9f2dbbbAl Viro	if (dentry->d_inode) {
30479714f72d3b964611997de512cb29198c9f2dbbbAl Viro		struct kstat stat;
30579714f72d3b964611997de512cb29198c9f2dbbbAl Viro		err = vfs_getattr(parent.mnt, dentry, &stat);
30679714f72d3b964611997de512cb29198c9f2dbbbAl Viro		if (!err && dev_mynode(dev, dentry->d_inode, &stat)) {
30779714f72d3b964611997de512cb29198c9f2dbbbAl Viro			struct iattr newattrs;
30879714f72d3b964611997de512cb29198c9f2dbbbAl Viro			/*
30979714f72d3b964611997de512cb29198c9f2dbbbAl Viro			 * before unlinking this node, reset permissions
31079714f72d3b964611997de512cb29198c9f2dbbbAl Viro			 * of possible references like hardlinks
31179714f72d3b964611997de512cb29198c9f2dbbbAl Viro			 */
31291fa2ccaa87368314527ea7518c545063662d67fEric W. Biederman			newattrs.ia_uid = GLOBAL_ROOT_UID;
31391fa2ccaa87368314527ea7518c545063662d67fEric W. Biederman			newattrs.ia_gid = GLOBAL_ROOT_GID;
31479714f72d3b964611997de512cb29198c9f2dbbbAl Viro			newattrs.ia_mode = stat.mode & ~0777;
31579714f72d3b964611997de512cb29198c9f2dbbbAl Viro			newattrs.ia_valid =
31679714f72d3b964611997de512cb29198c9f2dbbbAl Viro				ATTR_UID|ATTR_GID|ATTR_MODE;
31779714f72d3b964611997de512cb29198c9f2dbbbAl Viro			mutex_lock(&dentry->d_inode->i_mutex);
31879714f72d3b964611997de512cb29198c9f2dbbbAl Viro			notify_change(dentry, &newattrs);
31979714f72d3b964611997de512cb29198c9f2dbbbAl Viro			mutex_unlock(&dentry->d_inode->i_mutex);
32079714f72d3b964611997de512cb29198c9f2dbbbAl Viro			err = vfs_unlink(parent.dentry->d_inode, dentry);
32179714f72d3b964611997de512cb29198c9f2dbbbAl Viro			if (!err || err == -ENOENT)
32279714f72d3b964611997de512cb29198c9f2dbbbAl Viro				deleted = 1;
3232b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		}
3242b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	} else {
32579714f72d3b964611997de512cb29198c9f2dbbbAl Viro		err = -ENOENT;
3262b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	}
32779714f72d3b964611997de512cb29198c9f2dbbbAl Viro	dput(dentry);
32879714f72d3b964611997de512cb29198c9f2dbbbAl Viro	mutex_unlock(&parent.dentry->d_inode->i_mutex);
3292b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
33079714f72d3b964611997de512cb29198c9f2dbbbAl Viro	path_put(&parent);
3312b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	if (deleted && strchr(nodename, '/'))
3322b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		delete_path(nodename);
3332b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	return err;
3342b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers}
3352b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
3362b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers/*
3372b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers * If configured, or requested by the commandline, devtmpfs will be
3382b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers * auto-mounted after the kernel mounted the root filesystem.
3392b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers */
340073120cc28ad9f6003452c8bb9d15a87b1820201Kay Sieversint devtmpfs_mount(const char *mntdir)
3412b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers{
3422b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	int err;
3432b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
344fc14f2fef682df677d64a145256dbd263df2aa7bAl Viro	if (!mount_dev)
3452b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		return 0;
3462b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
3472780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	if (!thread)
3482b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		return 0;
3492b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
350073120cc28ad9f6003452c8bb9d15a87b1820201Kay Sievers	err = sys_mount("devtmpfs", (char *)mntdir, "devtmpfs", MS_SILENT, NULL);
3512b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	if (err)
3522b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		printk(KERN_INFO "devtmpfs: error mounting %i\n", err);
3532b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	else
3542b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		printk(KERN_INFO "devtmpfs: mounted\n");
3552b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	return err;
3562b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers}
3572b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
358f9e0b159dbff693bacb64a929e04f442df985b50Arnaud Lacombestatic DECLARE_COMPLETION(setup_done);
3592780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
360fbd48a69a0b576dd8cba01b2b4fc24fad76f1b68Al Virostatic int handle(const char *name, umode_t mode, struct device *dev)
3612780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro{
3622780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	if (mode)
3632780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro		return handle_create(name, mode, dev);
3642780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	else
3652780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro		return handle_remove(name, dev);
3662780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro}
3672780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
3682780f1ff6aec0cf708a61c022d475bfcaa648965Al Virostatic int devtmpfsd(void *p)
3692780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro{
3702780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	char options[] = "mode=0755";
3712780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	int *err = p;
3722780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	*err = sys_unshare(CLONE_NEWNS);
3732780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	if (*err)
3742780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro		goto out;
3752780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	*err = sys_mount("devtmpfs", "/", "devtmpfs", MS_SILENT, options);
3762780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	if (*err)
3772780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro		goto out;
3782780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	sys_chdir("/.."); /* will traverse into overmounted root */
3792780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	sys_chroot(".");
3802780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	complete(&setup_done);
3812780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	while (1) {
3822780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro		spin_lock(&req_lock);
3832780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro		while (requests) {
3842780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro			struct req *req = requests;
3852780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro			requests = NULL;
3862780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro			spin_unlock(&req_lock);
3872780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro			while (req) {
388e13889bab3c6b5c839075086d28fe05f71984ddaAl Viro				struct req *next = req->next;
3892780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro				req->err = handle(req->name, req->mode, req->dev);
3902780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro				complete(&req->done);
391e13889bab3c6b5c839075086d28fe05f71984ddaAl Viro				req = next;
3922780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro			}
3932780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro			spin_lock(&req_lock);
3942780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro		}
39565e6757be42ddf0a9115ec0e6af268fec9727359Kautuk Consul		__set_current_state(TASK_INTERRUPTIBLE);
3962780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro		spin_unlock(&req_lock);
3972780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro		schedule();
3982780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	}
3992780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	return 0;
4002780f1ff6aec0cf708a61c022d475bfcaa648965Al Viroout:
4012780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	complete(&setup_done);
4022780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	return *err;
4032780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro}
4042780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
4052b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers/*
4062b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers * Create devtmpfs instance, driver-core devices will add their device
4072b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers * nodes here.
4082b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers */
4092b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sieversint __init devtmpfs_init(void)
4102b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers{
4112780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	int err = register_filesystem(&dev_fs_type);
4122b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	if (err) {
4132b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		printk(KERN_ERR "devtmpfs: unable to register devtmpfs "
4142b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		       "type %i\n", err);
4152b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		return err;
4162b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	}
4172b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
4182780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	thread = kthread_run(devtmpfsd, &err, "kdevtmpfs");
4192780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	if (!IS_ERR(thread)) {
4202780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro		wait_for_completion(&setup_done);
4212780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	} else {
4222780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro		err = PTR_ERR(thread);
4232780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro		thread = NULL;
4242780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	}
4252780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro
4262780f1ff6aec0cf708a61c022d475bfcaa648965Al Viro	if (err) {
4272b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		printk(KERN_ERR "devtmpfs: unable to create devtmpfs %i\n", err);
4282b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		unregister_filesystem(&dev_fs_type);
4292b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers		return err;
4302b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	}
4312b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers
4322b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	printk(KERN_INFO "devtmpfs: initialized\n");
4332b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers	return 0;
4342b2af54a5bb6f7e80ccf78f20084b93c398c3a8bKay Sievers}
435