summaryrefslogtreecommitdiffstats
path: root/sys/sys/conf.h
diff options
context:
space:
mode:
authorkib <kib@FreeBSD.org>2016-01-07 20:08:02 +0000
committerkib <kib@FreeBSD.org>2016-01-07 20:08:02 +0000
commit3277da17a15d25dfa945d1d3e73229600fb919f0 (patch)
treeb2b1a4b261696203ad9e7f7173ec19efabf48685 /sys/sys/conf.h
parentd6b33ca987ecc9d932cfe376a81befcf2440ad0a (diff)
downloadFreeBSD-src-3277da17a15d25dfa945d1d3e73229600fb919f0.zip
FreeBSD-src-3277da17a15d25dfa945d1d3e73229600fb919f0.tar.gz
Provide yet another KPI for cdev creation, make_dev_s(9).
Immediate problem fixed by the new KPI is the long-standing race between device creation and assignments to cdev->si_drv1 and cdev->si_drv2, which allows the window where cdevsw methods might be called with si_drv1,2 fields not yet set. Devices typically checked for NULL and returned spurious errors to usermode, and often left some methods unchecked. The new function interface is designed to be extensible, which should allow to add more features to make_dev_s(9) without inventing yet another name for function to create devices, while maintaining KPI and even KBI backward-compatibility. Reviewed by: hps, jhb Sponsored by: The FreeBSD Foundation MFC after: 3 weeks Differential revision: https://reviews.freebsd.org/D4746
Diffstat (limited to 'sys/sys/conf.h')
-rw-r--r--sys/sys/conf.h30
1 files changed, 24 insertions, 6 deletions
diff --git a/sys/sys/conf.h b/sys/sys/conf.h
index 4681acd..a0dbc72 100644
--- a/sys/sys/conf.h
+++ b/sys/sys/conf.h
@@ -226,6 +226,28 @@ void clone_cleanup(struct clonedevs **);
#define CLONE_FLAG0 (CLONE_UNITMASK + 1)
int clone_create(struct clonedevs **, struct cdevsw *, int *unit, struct cdev **dev, int extra);
+#define MAKEDEV_REF 0x01
+#define MAKEDEV_WHTOUT 0x02
+#define MAKEDEV_NOWAIT 0x04
+#define MAKEDEV_WAITOK 0x08
+#define MAKEDEV_ETERNAL 0x10
+#define MAKEDEV_CHECKNAME 0x20
+struct make_dev_args {
+ size_t mda_size;
+ int mda_flags;
+ struct cdevsw *mda_devsw;
+ struct ucred *mda_cr;
+ uid_t mda_uid;
+ gid_t mda_gid;
+ int mda_mode;
+ int mda_unit;
+ void *mda_si_drv1;
+ void *mda_si_drv2;
+};
+void make_dev_args_init_impl(struct make_dev_args *_args, size_t _sz);
+#define make_dev_args_init(a) \
+ make_dev_args_init_impl((a), sizeof(struct make_dev_args))
+
int count_dev(struct cdev *_dev);
void delist_dev(struct cdev *_dev);
void destroy_dev(struct cdev *_dev);
@@ -245,12 +267,6 @@ struct cdev *make_dev(struct cdevsw *_devsw, int _unit, uid_t _uid, gid_t _gid,
struct cdev *make_dev_cred(struct cdevsw *_devsw, int _unit,
struct ucred *_cr, uid_t _uid, gid_t _gid, int _perms,
const char *_fmt, ...) __printflike(7, 8);
-#define MAKEDEV_REF 0x01
-#define MAKEDEV_WHTOUT 0x02
-#define MAKEDEV_NOWAIT 0x04
-#define MAKEDEV_WAITOK 0x08
-#define MAKEDEV_ETERNAL 0x10
-#define MAKEDEV_CHECKNAME 0x20
struct cdev *make_dev_credf(int _flags,
struct cdevsw *_devsw, int _unit,
struct ucred *_cr, uid_t _uid, gid_t _gid, int _mode,
@@ -258,6 +274,8 @@ struct cdev *make_dev_credf(int _flags,
int make_dev_p(int _flags, struct cdev **_cdev, struct cdevsw *_devsw,
struct ucred *_cr, uid_t _uid, gid_t _gid, int _mode,
const char *_fmt, ...) __printflike(8, 9);
+int make_dev_s(struct make_dev_args *_args, struct cdev **_cdev,
+ const char *_fmt, ...) __printflike(3, 4);
struct cdev *make_dev_alias(struct cdev *_pdev, const char *_fmt, ...)
__printflike(2, 3);
int make_dev_alias_p(int _flags, struct cdev **_cdev, struct cdev *_pdev,
OpenPOWER on IntegriCloud