Commit 19051c5035d217e572672a2ca9db06c1cef50e9b
1 parent
8882b39421
Exists in
master
and in
7 other branches
mm: bdi: fix race in bdi_class device creation
There is a race from when a device is created with device_create() and then the drvdata is set with a call to dev_set_drvdata() in which a sysfs file could be open, yet the drvdata will be NULL, causing all sorts of bad things to happen. This patch fixes the problem by using the new function, device_create_vargs(). Many thanks to Arthur Jones <ajones@riverbed.com> for reporting the bug, and testing patches out. Cc: Kay Sievers <kay.sievers@vrfy.org> Cc: Arthur Jones <ajones@riverbed.com> Cc: Peter Zijlstra <a.p.zijlstra@chello.nl> Cc: Miklos Szeredi <mszeredi@suse.cz> Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
Showing 1 changed file with 2 additions and 10 deletions Side-by-side Diff
mm/backing-dev.c
... | ... | @@ -172,30 +172,22 @@ |
172 | 172 | int bdi_register(struct backing_dev_info *bdi, struct device *parent, |
173 | 173 | const char *fmt, ...) |
174 | 174 | { |
175 | - char *name; | |
176 | 175 | va_list args; |
177 | 176 | int ret = 0; |
178 | 177 | struct device *dev; |
179 | 178 | |
180 | 179 | va_start(args, fmt); |
181 | - name = kvasprintf(GFP_KERNEL, fmt, args); | |
180 | + dev = device_create_vargs(bdi_class, parent, MKDEV(0, 0), bdi, fmt, args); | |
182 | 181 | va_end(args); |
183 | - | |
184 | - if (!name) | |
185 | - return -ENOMEM; | |
186 | - | |
187 | - dev = device_create(bdi_class, parent, MKDEV(0, 0), name); | |
188 | 182 | if (IS_ERR(dev)) { |
189 | 183 | ret = PTR_ERR(dev); |
190 | 184 | goto exit; |
191 | 185 | } |
192 | 186 | |
193 | 187 | bdi->dev = dev; |
194 | - dev_set_drvdata(bdi->dev, bdi); | |
195 | - bdi_debug_register(bdi, name); | |
188 | + bdi_debug_register(bdi, dev_name(dev)); | |
196 | 189 | |
197 | 190 | exit: |
198 | - kfree(name); | |
199 | 191 | return ret; |
200 | 192 | } |
201 | 193 | EXPORT_SYMBOL(bdi_register); |