aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorGreg Kroah-Hartman <gregkh@suse.de>2008-05-15 16:44:08 -0400
committerGreg Kroah-Hartman <gregkh@suse.de>2008-05-20 16:31:53 -0400
commit8882b39421bae317e3ee864edd845e994307ce16 (patch)
treecef24e2a04ad6716d37af2fabfe5f0a72dfe44b7
parentc110a2bd82676a8f124cf4dfc39339fd366f0e59 (diff)
Driver core: add device_create_vargs and device_create_drvdata
We want to have the drvdata field set properly when creating the device as sysfs callbacks can assume it is present and it can race the later setting of this field. So, create two new functions, deviec_create_vargs() and device_create_drvdata() that take this new field. device_create_drvdata() will go away in 2.6.27 as the drvdata field will just be moved to the device_create() call as it should be. Cc: Kay Sievers <kay.sievers@vrfy.org> Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
-rw-r--r--drivers/base/core.c85
-rw-r--r--include/linux/device.h12
2 files changed, 91 insertions, 6 deletions
diff --git a/drivers/base/core.c b/drivers/base/core.c
index be288b5e4180..f861c2b1dcff 100644
--- a/drivers/base/core.c
+++ b/drivers/base/core.c
@@ -1084,11 +1084,13 @@ static void device_create_release(struct device *dev)
1084} 1084}
1085 1085
1086/** 1086/**
1087 * device_create - creates a device and registers it with sysfs 1087 * device_create_vargs - creates a device and registers it with sysfs
1088 * @class: pointer to the struct class that this device should be registered to 1088 * @class: pointer to the struct class that this device should be registered to
1089 * @parent: pointer to the parent struct device of this new device, if any 1089 * @parent: pointer to the parent struct device of this new device, if any
1090 * @devt: the dev_t for the char device to be added 1090 * @devt: the dev_t for the char device to be added
1091 * @drvdata: the data to be added to the device for callbacks
1091 * @fmt: string for the device's name 1092 * @fmt: string for the device's name
1093 * @args: va_list for the device's name
1092 * 1094 *
1093 * This function can be used by char device classes. A struct device 1095 * This function can be used by char device classes. A struct device
1094 * will be created in sysfs, registered to the specified class. 1096 * will be created in sysfs, registered to the specified class.
@@ -1104,10 +1106,10 @@ static void device_create_release(struct device *dev)
1104 * Note: the struct class passed to this function must have previously 1106 * Note: the struct class passed to this function must have previously
1105 * been created with a call to class_create(). 1107 * been created with a call to class_create().
1106 */ 1108 */
1107struct device *device_create(struct class *class, struct device *parent, 1109struct device *device_create_vargs(struct class *class, struct device *parent,
1108 dev_t devt, const char *fmt, ...) 1110 dev_t devt, void *drvdata, const char *fmt,
1111 va_list args)
1109{ 1112{
1110 va_list args;
1111 struct device *dev = NULL; 1113 struct device *dev = NULL;
1112 int retval = -ENODEV; 1114 int retval = -ENODEV;
1113 1115
@@ -1124,10 +1126,9 @@ struct device *device_create(struct class *class, struct device *parent,
1124 dev->class = class; 1126 dev->class = class;
1125 dev->parent = parent; 1127 dev->parent = parent;
1126 dev->release = device_create_release; 1128 dev->release = device_create_release;
1129 dev_set_drvdata(dev, drvdata);
1127 1130
1128 va_start(args, fmt);
1129 vsnprintf(dev->bus_id, BUS_ID_SIZE, fmt, args); 1131 vsnprintf(dev->bus_id, BUS_ID_SIZE, fmt, args);
1130 va_end(args);
1131 retval = device_register(dev); 1132 retval = device_register(dev);
1132 if (retval) 1133 if (retval)
1133 goto error; 1134 goto error;
@@ -1138,6 +1139,78 @@ error:
1138 kfree(dev); 1139 kfree(dev);
1139 return ERR_PTR(retval); 1140 return ERR_PTR(retval);
1140} 1141}
1142EXPORT_SYMBOL_GPL(device_create_vargs);
1143
1144/**
1145 * device_create_drvdata - creates a device and registers it with sysfs
1146 * @class: pointer to the struct class that this device should be registered to
1147 * @parent: pointer to the parent struct device of this new device, if any
1148 * @devt: the dev_t for the char device to be added
1149 * @drvdata: the data to be added to the device for callbacks
1150 * @fmt: string for the device's name
1151 *
1152 * This function can be used by char device classes. A struct device
1153 * will be created in sysfs, registered to the specified class.
1154 *
1155 * A "dev" file will be created, showing the dev_t for the device, if
1156 * the dev_t is not 0,0.
1157 * If a pointer to a parent struct device is passed in, the newly created
1158 * struct device will be a child of that device in sysfs.
1159 * The pointer to the struct device will be returned from the call.
1160 * Any further sysfs files that might be required can be created using this
1161 * pointer.
1162 *
1163 * Note: the struct class passed to this function must have previously
1164 * been created with a call to class_create().
1165 */
1166struct device *device_create_drvdata(struct class *class,
1167 struct device *parent,
1168 dev_t devt,
1169 void *drvdata,
1170 const char *fmt, ...)
1171{
1172 va_list vargs;
1173 struct device *dev;
1174
1175 va_start(vargs, fmt);
1176 dev = device_create_vargs(class, parent, devt, drvdata, fmt, vargs);
1177 va_end(vargs);
1178 return dev;
1179}
1180EXPORT_SYMBOL_GPL(device_create_drvdata);
1181
1182/**
1183 * device_create - creates a device and registers it with sysfs
1184 * @class: pointer to the struct class that this device should be registered to
1185 * @parent: pointer to the parent struct device of this new device, if any
1186 * @devt: the dev_t for the char device to be added
1187 * @fmt: string for the device's name
1188 *
1189 * This function can be used by char device classes. A struct device
1190 * will be created in sysfs, registered to the specified class.
1191 *
1192 * A "dev" file will be created, showing the dev_t for the device, if
1193 * the dev_t is not 0,0.
1194 * If a pointer to a parent struct device is passed in, the newly created
1195 * struct device will be a child of that device in sysfs.
1196 * The pointer to the struct device will be returned from the call.
1197 * Any further sysfs files that might be required can be created using this
1198 * pointer.
1199 *
1200 * Note: the struct class passed to this function must have previously
1201 * been created with a call to class_create().
1202 */
1203struct device *device_create(struct class *class, struct device *parent,
1204 dev_t devt, const char *fmt, ...)
1205{
1206 va_list vargs;
1207 struct device *dev;
1208
1209 va_start(vargs, fmt);
1210 dev = device_create_vargs(class, parent, devt, NULL, fmt, vargs);
1211 va_end(vargs);
1212 return dev;
1213}
1141EXPORT_SYMBOL_GPL(device_create); 1214EXPORT_SYMBOL_GPL(device_create);
1142 1215
1143static int __match_devt(struct device *dev, void *data) 1216static int __match_devt(struct device *dev, void *data)
diff --git a/include/linux/device.h b/include/linux/device.h
index 15e9fa3ad3af..14616e80213c 100644
--- a/include/linux/device.h
+++ b/include/linux/device.h
@@ -449,9 +449,21 @@ extern int __must_check device_reprobe(struct device *dev);
449/* 449/*
450 * Easy functions for dynamically creating devices on the fly 450 * Easy functions for dynamically creating devices on the fly
451 */ 451 */
452extern struct device *device_create_vargs(struct class *cls,
453 struct device *parent,
454 dev_t devt,
455 void *drvdata,
456 const char *fmt,
457 va_list vargs);
452extern struct device *device_create(struct class *cls, struct device *parent, 458extern struct device *device_create(struct class *cls, struct device *parent,
453 dev_t devt, const char *fmt, ...) 459 dev_t devt, const char *fmt, ...)
454 __attribute__((format(printf, 4, 5))); 460 __attribute__((format(printf, 4, 5)));
461extern struct device *device_create_drvdata(struct class *cls,
462 struct device *parent,
463 dev_t devt,
464 void *drvdata,
465 const char *fmt, ...)
466 __attribute__((format(printf, 5, 6)));
455extern void device_destroy(struct class *cls, dev_t devt); 467extern void device_destroy(struct class *cls, dev_t devt);
456 468
457/* 469/*