Commit | Line | Data |
---|---|---|
1da177e4 LT |
1 | #include <linux/vmalloc.h> |
2 | #include <linux/module.h> | |
3 | #include <linux/fs.h> | |
4 | #include <linux/mm.h> | |
5 | #include <linux/slab.h> | |
6 | #include <asm/uaccess.h> | |
b9dd6ffc | 7 | #include "oss/sound_firmware.h" |
1da177e4 LT |
8 | |
9 | static int do_mod_firmware_load(const char *fn, char **fp) | |
10 | { | |
11 | struct file* filp; | |
12 | long l; | |
13 | char *dp; | |
14 | loff_t pos; | |
15 | ||
16 | filp = filp_open(fn, 0, 0); | |
17 | if (IS_ERR(filp)) | |
18 | { | |
19 | printk(KERN_INFO "Unable to load '%s'.\n", fn); | |
20 | return 0; | |
21 | } | |
7bc56323 | 22 | l = filp->f_path.dentry->d_inode->i_size; |
1da177e4 LT |
23 | if (l <= 0 || l > 131072) |
24 | { | |
25 | printk(KERN_INFO "Invalid firmware '%s'\n", fn); | |
26 | filp_close(filp, current->files); | |
27 | return 0; | |
28 | } | |
29 | dp = vmalloc(l); | |
30 | if (dp == NULL) | |
31 | { | |
32 | printk(KERN_INFO "Out of memory loading '%s'.\n", fn); | |
33 | filp_close(filp, current->files); | |
34 | return 0; | |
35 | } | |
36 | pos = 0; | |
37 | if (vfs_read(filp, dp, l, &pos) != l) | |
38 | { | |
39 | printk(KERN_INFO "Failed to read '%s'.\n", fn); | |
40 | vfree(dp); | |
41 | filp_close(filp, current->files); | |
42 | return 0; | |
43 | } | |
44 | filp_close(filp, current->files); | |
45 | *fp = dp; | |
46 | return (int) l; | |
47 | } | |
48 | ||
49 | /** | |
50 | * mod_firmware_load - load sound driver firmware | |
51 | * @fn: filename | |
52 | * @fp: return for the buffer. | |
53 | * | |
54 | * Load the firmware for a sound module (up to 128K) into a buffer. | |
55 | * The buffer is returned in *fp. It is allocated with vmalloc so is | |
56 | * virtually linear and not DMAable. The caller should free it with | |
57 | * vfree when finished. | |
58 | * | |
59 | * The length of the buffer is returned on a successful load, the | |
60 | * value zero on a failure. | |
61 | * | |
62 | * Caution: This API is not recommended. Firmware should be loaded via | |
b9dd6ffc | 63 | * request_firmware. |
1da177e4 LT |
64 | */ |
65 | ||
66 | int mod_firmware_load(const char *fn, char **fp) | |
67 | { | |
68 | int r; | |
69 | mm_segment_t fs = get_fs(); | |
70 | ||
71 | set_fs(get_ds()); | |
72 | r = do_mod_firmware_load(fn, fp); | |
73 | set_fs(fs); | |
74 | return r; | |
75 | } | |
b9dd6ffc | 76 | EXPORT_SYMBOL(mod_firmware_load); |
1da177e4 | 77 | |
b9dd6ffc | 78 | MODULE_LICENSE("GPL"); |