aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--block/genhd.c3
-rw-r--r--drivers/base/core.c17
-rw-r--r--drivers/base/devtmpfs.c27
-rw-r--r--drivers/usb/core/usb.c3
-rw-r--r--include/linux/device.h7
5 files changed, 39 insertions, 18 deletions
diff --git a/block/genhd.c b/block/genhd.c
index 3c001fba80c7..dfcec431ceea 100644
--- a/block/genhd.c
+++ b/block/genhd.c
@@ -1111,7 +1111,8 @@ struct class block_class = {
1111 .name = "block", 1111 .name = "block",
1112}; 1112};
1113 1113
1114static char *block_devnode(struct device *dev, umode_t *mode) 1114static char *block_devnode(struct device *dev, umode_t *mode,
1115 uid_t *uid, gid_t *gid)
1115{ 1116{
1116 struct gendisk *disk = dev_to_disk(dev); 1117 struct gendisk *disk = dev_to_disk(dev);
1117 1118
diff --git a/drivers/base/core.c b/drivers/base/core.c
index a7391a30cb29..8a428b51089d 100644
--- a/drivers/base/core.c
+++ b/drivers/base/core.c
@@ -283,15 +283,21 @@ static int dev_uevent(struct kset *kset, struct kobject *kobj,
283 const char *tmp; 283 const char *tmp;
284 const char *name; 284 const char *name;
285 umode_t mode = 0; 285 umode_t mode = 0;
286 uid_t uid = 0;
287 gid_t gid = 0;
286 288
287 add_uevent_var(env, "MAJOR=%u", MAJOR(dev->devt)); 289 add_uevent_var(env, "MAJOR=%u", MAJOR(dev->devt));
288 add_uevent_var(env, "MINOR=%u", MINOR(dev->devt)); 290 add_uevent_var(env, "MINOR=%u", MINOR(dev->devt));
289 name = device_get_devnode(dev, &mode, &tmp); 291 name = device_get_devnode(dev, &mode, &uid, &gid, &tmp);
290 if (name) { 292 if (name) {
291 add_uevent_var(env, "DEVNAME=%s", name); 293 add_uevent_var(env, "DEVNAME=%s", name);
292 kfree(tmp);
293 if (mode) 294 if (mode)
294 add_uevent_var(env, "DEVMODE=%#o", mode & 0777); 295 add_uevent_var(env, "DEVMODE=%#o", mode & 0777);
296 if (uid)
297 add_uevent_var(env, "DEVUID=%u", uid);
298 if (gid)
299 add_uevent_var(env, "DEVGID=%u", gid);
300 kfree(tmp);
295 } 301 }
296 } 302 }
297 303
@@ -1281,6 +1287,8 @@ static struct device *next_device(struct klist_iter *i)
1281 * device_get_devnode - path of device node file 1287 * device_get_devnode - path of device node file
1282 * @dev: device 1288 * @dev: device
1283 * @mode: returned file access mode 1289 * @mode: returned file access mode
1290 * @uid: returned file owner
1291 * @gid: returned file group
1284 * @tmp: possibly allocated string 1292 * @tmp: possibly allocated string
1285 * 1293 *
1286 * Return the relative path of a possible device node. 1294 * Return the relative path of a possible device node.
@@ -1289,7 +1297,8 @@ static struct device *next_device(struct klist_iter *i)
1289 * freed by the caller. 1297 * freed by the caller.
1290 */ 1298 */
1291const char *device_get_devnode(struct device *dev, 1299const char *device_get_devnode(struct device *dev,
1292 umode_t *mode, const char **tmp) 1300 umode_t *mode, uid_t *uid, gid_t *gid,
1301 const char **tmp)
1293{ 1302{
1294 char *s; 1303 char *s;
1295 1304
@@ -1297,7 +1306,7 @@ const char *device_get_devnode(struct device *dev,
1297 1306
1298 /* the device type may provide a specific name */ 1307 /* the device type may provide a specific name */
1299 if (dev->type && dev->type->devnode) 1308 if (dev->type && dev->type->devnode)
1300 *tmp = dev->type->devnode(dev, mode); 1309 *tmp = dev->type->devnode(dev, mode, uid, gid);
1301 if (*tmp) 1310 if (*tmp)
1302 return *tmp; 1311 return *tmp;
1303 1312
diff --git a/drivers/base/devtmpfs.c b/drivers/base/devtmpfs.c
index 01fc5b07f951..fda52563677f 100644
--- a/drivers/base/devtmpfs.c
+++ b/drivers/base/devtmpfs.c
@@ -41,6 +41,8 @@ static struct req {
41 int err; 41 int err;
42 const char *name; 42 const char *name;
43 umode_t mode; /* 0 => delete */ 43 umode_t mode; /* 0 => delete */
44 uid_t uid;
45 gid_t gid;
44 struct device *dev; 46 struct device *dev;
45} *requests; 47} *requests;
46 48
@@ -85,7 +87,9 @@ int devtmpfs_create_node(struct device *dev)
85 return 0; 87 return 0;
86 88
87 req.mode = 0; 89 req.mode = 0;
88 req.name = device_get_devnode(dev, &req.mode, &tmp); 90 req.uid = 0;
91 req.gid = 0;
92 req.name = device_get_devnode(dev, &req.mode, &req.uid, &req.gid, &tmp);
89 if (!req.name) 93 if (!req.name)
90 return -ENOMEM; 94 return -ENOMEM;
91 95
@@ -121,7 +125,7 @@ int devtmpfs_delete_node(struct device *dev)
121 if (!thread) 125 if (!thread)
122 return 0; 126 return 0;
123 127
124 req.name = device_get_devnode(dev, NULL, &tmp); 128 req.name = device_get_devnode(dev, NULL, NULL, NULL, &tmp);
125 if (!req.name) 129 if (!req.name)
126 return -ENOMEM; 130 return -ENOMEM;
127 131
@@ -187,7 +191,8 @@ static int create_path(const char *nodepath)
187 return err; 191 return err;
188} 192}
189 193
190static int handle_create(const char *nodename, umode_t mode, struct device *dev) 194static int handle_create(const char *nodename, umode_t mode, uid_t uid,
195 gid_t gid, struct device *dev)
191{ 196{
192 struct dentry *dentry; 197 struct dentry *dentry;
193 struct path path; 198 struct path path;
@@ -201,14 +206,14 @@ static int handle_create(const char *nodename, umode_t mode, struct device *dev)
201 if (IS_ERR(dentry)) 206 if (IS_ERR(dentry))
202 return PTR_ERR(dentry); 207 return PTR_ERR(dentry);
203 208
204 err = vfs_mknod(path.dentry->d_inode, 209 err = vfs_mknod(path.dentry->d_inode, dentry, mode, dev->devt);
205 dentry, mode, dev->devt);
206 if (!err) { 210 if (!err) {
207 struct iattr newattrs; 211 struct iattr newattrs;
208 212
209 /* fixup possibly umasked mode */
210 newattrs.ia_mode = mode; 213 newattrs.ia_mode = mode;
211 newattrs.ia_valid = ATTR_MODE; 214 newattrs.ia_uid = uid;
215 newattrs.ia_gid = gid;
216 newattrs.ia_valid = ATTR_MODE|ATTR_UID|ATTR_GID;
212 mutex_lock(&dentry->d_inode->i_mutex); 217 mutex_lock(&dentry->d_inode->i_mutex);
213 notify_change(dentry, &newattrs); 218 notify_change(dentry, &newattrs);
214 mutex_unlock(&dentry->d_inode->i_mutex); 219 mutex_unlock(&dentry->d_inode->i_mutex);
@@ -358,10 +363,11 @@ int devtmpfs_mount(const char *mntdir)
358 363
359static DECLARE_COMPLETION(setup_done); 364static DECLARE_COMPLETION(setup_done);
360 365
361static int handle(const char *name, umode_t mode, struct device *dev) 366static int handle(const char *name, umode_t mode, uid_t uid, gid_t gid,
367 struct device *dev)
362{ 368{
363 if (mode) 369 if (mode)
364 return handle_create(name, mode, dev); 370 return handle_create(name, mode, uid, gid, dev);
365 else 371 else
366 return handle_remove(name, dev); 372 return handle_remove(name, dev);
367} 373}
@@ -387,7 +393,8 @@ static int devtmpfsd(void *p)
387 spin_unlock(&req_lock); 393 spin_unlock(&req_lock);
388 while (req) { 394 while (req) {
389 struct req *next = req->next; 395 struct req *next = req->next;
390 req->err = handle(req->name, req->mode, req->dev); 396 req->err = handle(req->name, req->mode,
397 req->uid, req->gid, req->dev);
391 complete(&req->done); 398 complete(&req->done);
392 req = next; 399 req = next;
393 } 400 }
diff --git a/drivers/usb/core/usb.c b/drivers/usb/core/usb.c
index f81b92572735..17002832abd9 100644
--- a/drivers/usb/core/usb.c
+++ b/drivers/usb/core/usb.c
@@ -317,7 +317,8 @@ static const struct dev_pm_ops usb_device_pm_ops = {
317#endif /* CONFIG_PM */ 317#endif /* CONFIG_PM */
318 318
319 319
320static char *usb_devnode(struct device *dev, umode_t *mode) 320static char *usb_devnode(struct device *dev,
321 umode_t *mode, uid_t *uid, gid_t *gid)
321{ 322{
322 struct usb_device *usb_dev; 323 struct usb_device *usb_dev;
323 324
diff --git a/include/linux/device.h b/include/linux/device.h
index 4a7c4a84afee..851b85c7101e 100644
--- a/include/linux/device.h
+++ b/include/linux/device.h
@@ -25,6 +25,7 @@
25#include <linux/pm.h> 25#include <linux/pm.h>
26#include <linux/atomic.h> 26#include <linux/atomic.h>
27#include <linux/ratelimit.h> 27#include <linux/ratelimit.h>
28#include <linux/uidgid.h>
28#include <asm/device.h> 29#include <asm/device.h>
29 30
30struct device; 31struct device;
@@ -465,7 +466,8 @@ struct device_type {
465 const char *name; 466 const char *name;
466 const struct attribute_group **groups; 467 const struct attribute_group **groups;
467 int (*uevent)(struct device *dev, struct kobj_uevent_env *env); 468 int (*uevent)(struct device *dev, struct kobj_uevent_env *env);
468 char *(*devnode)(struct device *dev, umode_t *mode); 469 char *(*devnode)(struct device *dev, umode_t *mode,
470 uid_t *uid, gid_t *gid);
469 void (*release)(struct device *dev); 471 void (*release)(struct device *dev);
470 472
471 const struct dev_pm_ops *pm; 473 const struct dev_pm_ops *pm;
@@ -843,7 +845,8 @@ extern int device_rename(struct device *dev, const char *new_name);
843extern int device_move(struct device *dev, struct device *new_parent, 845extern int device_move(struct device *dev, struct device *new_parent,
844 enum dpm_order dpm_order); 846 enum dpm_order dpm_order);
845extern const char *device_get_devnode(struct device *dev, 847extern const char *device_get_devnode(struct device *dev,
846 umode_t *mode, const char **tmp); 848 umode_t *mode, uid_t *uid, gid_t *gid,
849 const char **tmp);
847extern void *dev_get_drvdata(const struct device *dev); 850extern void *dev_get_drvdata(const struct device *dev);
848extern int dev_set_drvdata(struct device *dev, void *data); 851extern int dev_set_drvdata(struct device *dev, void *data);
849 852