diff options
Diffstat (limited to 'arch/um/drivers')
-rw-r--r-- | arch/um/drivers/chan_user.c | 1 | ||||
-rw-r--r-- | arch/um/drivers/cow_sys.h | 2 | ||||
-rw-r--r-- | arch/um/drivers/daemon_user.c | 4 | ||||
-rw-r--r-- | arch/um/drivers/fd.c | 2 | ||||
-rw-r--r-- | arch/um/drivers/hostaudio_kern.c | 2 | ||||
-rw-r--r-- | arch/um/drivers/mcast_user.c | 3 | ||||
-rw-r--r-- | arch/um/drivers/net_user.c | 2 | ||||
-rw-r--r-- | arch/um/drivers/port_user.c | 2 | ||||
-rw-r--r-- | arch/um/drivers/pty.c | 2 | ||||
-rw-r--r-- | arch/um/drivers/random.c | 122 | ||||
-rw-r--r-- | arch/um/drivers/slip_user.c | 2 | ||||
-rw-r--r-- | arch/um/drivers/tty.c | 2 | ||||
-rw-r--r-- | arch/um/drivers/ubd_kern.c | 4 | ||||
-rw-r--r-- | arch/um/drivers/xterm.c | 2 |
14 files changed, 95 insertions, 57 deletions
diff --git a/arch/um/drivers/chan_user.c b/arch/um/drivers/chan_user.c index 025764089ac8..cfeb3f4a44af 100644 --- a/arch/um/drivers/chan_user.c +++ b/arch/um/drivers/chan_user.c | |||
@@ -11,6 +11,7 @@ | |||
11 | #include <termios.h> | 11 | #include <termios.h> |
12 | #include <sys/ioctl.h> | 12 | #include <sys/ioctl.h> |
13 | #include "chan_user.h" | 13 | #include "chan_user.h" |
14 | #include "kern_constants.h" | ||
14 | #include "os.h" | 15 | #include "os.h" |
15 | #include "um_malloc.h" | 16 | #include "um_malloc.h" |
16 | #include "user.h" | 17 | #include "user.h" |
diff --git a/arch/um/drivers/cow_sys.h b/arch/um/drivers/cow_sys.h index ca8c9e11a39b..f5701fd2ef90 100644 --- a/arch/um/drivers/cow_sys.h +++ b/arch/um/drivers/cow_sys.h | |||
@@ -8,7 +8,7 @@ | |||
8 | 8 | ||
9 | static inline void *cow_malloc(int size) | 9 | static inline void *cow_malloc(int size) |
10 | { | 10 | { |
11 | return kmalloc(size, UM_GFP_KERNEL); | 11 | return uml_kmalloc(size, UM_GFP_KERNEL); |
12 | } | 12 | } |
13 | 13 | ||
14 | static inline void cow_free(void *ptr) | 14 | static inline void cow_free(void *ptr) |
diff --git a/arch/um/drivers/daemon_user.c b/arch/um/drivers/daemon_user.c index f23c109a055c..f8e85e0bdace 100644 --- a/arch/um/drivers/daemon_user.c +++ b/arch/um/drivers/daemon_user.c | |||
@@ -34,7 +34,7 @@ static struct sockaddr_un *new_addr(void *name, int len) | |||
34 | { | 34 | { |
35 | struct sockaddr_un *sun; | 35 | struct sockaddr_un *sun; |
36 | 36 | ||
37 | sun = kmalloc(sizeof(struct sockaddr_un), UM_GFP_KERNEL); | 37 | sun = uml_kmalloc(sizeof(struct sockaddr_un), UM_GFP_KERNEL); |
38 | if (sun == NULL) { | 38 | if (sun == NULL) { |
39 | printk(UM_KERN_ERR "new_addr: allocation of sockaddr_un " | 39 | printk(UM_KERN_ERR "new_addr: allocation of sockaddr_un " |
40 | "failed\n"); | 40 | "failed\n"); |
@@ -83,7 +83,7 @@ static int connect_to_switch(struct daemon_data *pri) | |||
83 | goto out_close; | 83 | goto out_close; |
84 | } | 84 | } |
85 | 85 | ||
86 | sun = kmalloc(sizeof(struct sockaddr_un), UM_GFP_KERNEL); | 86 | sun = uml_kmalloc(sizeof(struct sockaddr_un), UM_GFP_KERNEL); |
87 | if (sun == NULL) { | 87 | if (sun == NULL) { |
88 | printk(UM_KERN_ERR "new_addr: allocation of sockaddr_un " | 88 | printk(UM_KERN_ERR "new_addr: allocation of sockaddr_un " |
89 | "failed\n"); | 89 | "failed\n"); |
diff --git a/arch/um/drivers/fd.c b/arch/um/drivers/fd.c index 0a2bb5b64b82..f5a981a16240 100644 --- a/arch/um/drivers/fd.c +++ b/arch/um/drivers/fd.c | |||
@@ -40,7 +40,7 @@ static void *fd_init(char *str, int device, const struct chan_opts *opts) | |||
40 | return NULL; | 40 | return NULL; |
41 | } | 41 | } |
42 | 42 | ||
43 | data = kmalloc(sizeof(*data), UM_GFP_KERNEL); | 43 | data = uml_kmalloc(sizeof(*data), UM_GFP_KERNEL); |
44 | if (data == NULL) | 44 | if (data == NULL) |
45 | return NULL; | 45 | return NULL; |
46 | 46 | ||
diff --git a/arch/um/drivers/hostaudio_kern.c b/arch/um/drivers/hostaudio_kern.c index ff1b22b69e9c..368219cc2366 100644 --- a/arch/um/drivers/hostaudio_kern.c +++ b/arch/um/drivers/hostaudio_kern.c | |||
@@ -154,7 +154,7 @@ static int hostaudio_ioctl(struct inode *inode, struct file *file, | |||
154 | case SNDCTL_DSP_SUBDIVIDE: | 154 | case SNDCTL_DSP_SUBDIVIDE: |
155 | case SNDCTL_DSP_SETFRAGMENT: | 155 | case SNDCTL_DSP_SETFRAGMENT: |
156 | if (get_user(data, (int __user *) arg)) | 156 | if (get_user(data, (int __user *) arg)) |
157 | return EFAULT; | 157 | return -EFAULT; |
158 | break; | 158 | break; |
159 | default: | 159 | default: |
160 | break; | 160 | break; |
diff --git a/arch/um/drivers/mcast_user.c b/arch/um/drivers/mcast_user.c index 5f647d7a7292..ee19e91568a2 100644 --- a/arch/um/drivers/mcast_user.c +++ b/arch/um/drivers/mcast_user.c | |||
@@ -15,6 +15,7 @@ | |||
15 | #include <unistd.h> | 15 | #include <unistd.h> |
16 | #include <errno.h> | 16 | #include <errno.h> |
17 | #include <netinet/in.h> | 17 | #include <netinet/in.h> |
18 | #include "kern_constants.h" | ||
18 | #include "mcast.h" | 19 | #include "mcast.h" |
19 | #include "net_user.h" | 20 | #include "net_user.h" |
20 | #include "um_malloc.h" | 21 | #include "um_malloc.h" |
@@ -24,7 +25,7 @@ static struct sockaddr_in *new_addr(char *addr, unsigned short port) | |||
24 | { | 25 | { |
25 | struct sockaddr_in *sin; | 26 | struct sockaddr_in *sin; |
26 | 27 | ||
27 | sin = kmalloc(sizeof(struct sockaddr_in), UM_GFP_KERNEL); | 28 | sin = uml_kmalloc(sizeof(struct sockaddr_in), UM_GFP_KERNEL); |
28 | if (sin == NULL) { | 29 | if (sin == NULL) { |
29 | printk(UM_KERN_ERR "new_addr: allocation of sockaddr_in " | 30 | printk(UM_KERN_ERR "new_addr: allocation of sockaddr_in " |
30 | "failed\n"); | 31 | "failed\n"); |
diff --git a/arch/um/drivers/net_user.c b/arch/um/drivers/net_user.c index abf2653f5517..9415dd9e63ef 100644 --- a/arch/um/drivers/net_user.c +++ b/arch/um/drivers/net_user.c | |||
@@ -222,7 +222,7 @@ static void change(char *dev, char *what, unsigned char *addr, | |||
222 | netmask[2], netmask[3]); | 222 | netmask[2], netmask[3]); |
223 | 223 | ||
224 | output_len = UM_KERN_PAGE_SIZE; | 224 | output_len = UM_KERN_PAGE_SIZE; |
225 | output = kmalloc(output_len, UM_GFP_KERNEL); | 225 | output = uml_kmalloc(output_len, UM_GFP_KERNEL); |
226 | if (output == NULL) | 226 | if (output == NULL) |
227 | printk(UM_KERN_ERR "change : failed to allocate output " | 227 | printk(UM_KERN_ERR "change : failed to allocate output " |
228 | "buffer\n"); | 228 | "buffer\n"); |
diff --git a/arch/um/drivers/port_user.c b/arch/um/drivers/port_user.c index d269ca387f10..b49bf56a56aa 100644 --- a/arch/um/drivers/port_user.c +++ b/arch/um/drivers/port_user.c | |||
@@ -47,7 +47,7 @@ static void *port_init(char *str, int device, const struct chan_opts *opts) | |||
47 | if (kern_data == NULL) | 47 | if (kern_data == NULL) |
48 | return NULL; | 48 | return NULL; |
49 | 49 | ||
50 | data = kmalloc(sizeof(*data), UM_GFP_KERNEL); | 50 | data = uml_kmalloc(sizeof(*data), UM_GFP_KERNEL); |
51 | if (data == NULL) | 51 | if (data == NULL) |
52 | goto err; | 52 | goto err; |
53 | 53 | ||
diff --git a/arch/um/drivers/pty.c b/arch/um/drivers/pty.c index 49c79dda6046..1113911dcb2b 100644 --- a/arch/um/drivers/pty.c +++ b/arch/um/drivers/pty.c | |||
@@ -29,7 +29,7 @@ static void *pty_chan_init(char *str, int device, const struct chan_opts *opts) | |||
29 | { | 29 | { |
30 | struct pty_chan *data; | 30 | struct pty_chan *data; |
31 | 31 | ||
32 | data = kmalloc(sizeof(*data), UM_GFP_KERNEL); | 32 | data = uml_kmalloc(sizeof(*data), UM_GFP_KERNEL); |
33 | if (data == NULL) | 33 | if (data == NULL) |
34 | return NULL; | 34 | return NULL; |
35 | 35 | ||
diff --git a/arch/um/drivers/random.c b/arch/um/drivers/random.c index 71f0959c1535..4949044773ba 100644 --- a/arch/um/drivers/random.c +++ b/arch/um/drivers/random.c | |||
@@ -1,4 +1,5 @@ | |||
1 | /* Copyright (C) 2005 Jeff Dike <jdike@addtoit.com> */ | 1 | /* Copyright (C) 2005 - 2008 Jeff Dike <jdike@{linux.intel,addtoit}.com> */ |
2 | |||
2 | /* Much of this ripped from drivers/char/hw_random.c, see there for other | 3 | /* Much of this ripped from drivers/char/hw_random.c, see there for other |
3 | * copyright. | 4 | * copyright. |
4 | * | 5 | * |
@@ -8,16 +9,18 @@ | |||
8 | #include <linux/sched.h> | 9 | #include <linux/sched.h> |
9 | #include <linux/module.h> | 10 | #include <linux/module.h> |
10 | #include <linux/fs.h> | 11 | #include <linux/fs.h> |
12 | #include <linux/interrupt.h> | ||
11 | #include <linux/miscdevice.h> | 13 | #include <linux/miscdevice.h> |
12 | #include <linux/delay.h> | 14 | #include <linux/delay.h> |
13 | #include <asm/uaccess.h> | 15 | #include <asm/uaccess.h> |
16 | #include "irq_kern.h" | ||
14 | #include "os.h" | 17 | #include "os.h" |
15 | 18 | ||
16 | /* | 19 | /* |
17 | * core module and version information | 20 | * core module and version information |
18 | */ | 21 | */ |
19 | #define RNG_VERSION "1.0.0" | 22 | #define RNG_VERSION "1.0.0" |
20 | #define RNG_MODULE_NAME "random" | 23 | #define RNG_MODULE_NAME "hw_random" |
21 | 24 | ||
22 | #define RNG_MISCDEV_MINOR 183 /* official */ | 25 | #define RNG_MISCDEV_MINOR 183 /* official */ |
23 | 26 | ||
@@ -26,47 +29,67 @@ | |||
26 | * protects against a module being loaded twice at the same time. | 29 | * protects against a module being loaded twice at the same time. |
27 | */ | 30 | */ |
28 | static int random_fd = -1; | 31 | static int random_fd = -1; |
32 | static DECLARE_WAIT_QUEUE_HEAD(host_read_wait); | ||
29 | 33 | ||
30 | static int rng_dev_open (struct inode *inode, struct file *filp) | 34 | static int rng_dev_open (struct inode *inode, struct file *filp) |
31 | { | 35 | { |
32 | /* enforce read-only access to this chrdev */ | 36 | /* enforce read-only access to this chrdev */ |
33 | if ((filp->f_mode & FMODE_READ) == 0) | 37 | if ((filp->f_mode & FMODE_READ) == 0) |
34 | return -EINVAL; | 38 | return -EINVAL; |
35 | if (filp->f_mode & FMODE_WRITE) | 39 | if ((filp->f_mode & FMODE_WRITE) != 0) |
36 | return -EINVAL; | 40 | return -EINVAL; |
37 | 41 | ||
38 | return 0; | 42 | return 0; |
39 | } | 43 | } |
40 | 44 | ||
45 | static atomic_t host_sleep_count = ATOMIC_INIT(0); | ||
46 | |||
41 | static ssize_t rng_dev_read (struct file *filp, char __user *buf, size_t size, | 47 | static ssize_t rng_dev_read (struct file *filp, char __user *buf, size_t size, |
42 | loff_t * offp) | 48 | loff_t *offp) |
43 | { | 49 | { |
44 | u32 data; | 50 | u32 data; |
45 | int n, ret = 0, have_data; | 51 | int n, ret = 0, have_data; |
46 | 52 | ||
47 | while(size){ | 53 | while (size) { |
48 | n = os_read_file(random_fd, &data, sizeof(data)); | 54 | n = os_read_file(random_fd, &data, sizeof(data)); |
49 | if(n > 0){ | 55 | if (n > 0) { |
50 | have_data = n; | 56 | have_data = n; |
51 | while (have_data && size) { | 57 | while (have_data && size) { |
52 | if (put_user((u8)data, buf++)) { | 58 | if (put_user((u8) data, buf++)) { |
53 | ret = ret ? : -EFAULT; | 59 | ret = ret ? : -EFAULT; |
54 | break; | 60 | break; |
55 | } | 61 | } |
56 | size--; | 62 | size--; |
57 | ret++; | 63 | ret++; |
58 | have_data--; | 64 | have_data--; |
59 | data>>=8; | 65 | data >>= 8; |
60 | } | 66 | } |
61 | } | 67 | } |
62 | else if(n == -EAGAIN){ | 68 | else if (n == -EAGAIN) { |
63 | if (filp->f_flags & O_NONBLOCK) | 69 | DECLARE_WAITQUEUE(wait, current); |
64 | return ret ? : -EAGAIN; | 70 | |
65 | 71 | if (filp->f_flags & O_NONBLOCK) | |
66 | if(need_resched()) | 72 | return ret ? : -EAGAIN; |
67 | schedule_timeout_interruptible(1); | 73 | |
68 | } | 74 | atomic_inc(&host_sleep_count); |
69 | else return n; | 75 | reactivate_fd(random_fd, RANDOM_IRQ); |
76 | add_sigio_fd(random_fd); | ||
77 | |||
78 | add_wait_queue(&host_read_wait, &wait); | ||
79 | set_task_state(current, TASK_INTERRUPTIBLE); | ||
80 | |||
81 | schedule(); | ||
82 | set_task_state(current, TASK_RUNNING); | ||
83 | remove_wait_queue(&host_read_wait, &wait); | ||
84 | |||
85 | if (atomic_dec_and_test(&host_sleep_count)) { | ||
86 | ignore_sigio_fd(random_fd); | ||
87 | deactivate_fd(random_fd, RANDOM_IRQ); | ||
88 | } | ||
89 | } | ||
90 | else | ||
91 | return n; | ||
92 | |||
70 | if (signal_pending (current)) | 93 | if (signal_pending (current)) |
71 | return ret ? : -ERESTARTSYS; | 94 | return ret ? : -ERESTARTSYS; |
72 | } | 95 | } |
@@ -86,6 +109,13 @@ static struct miscdevice rng_miscdev = { | |||
86 | &rng_chrdev_ops, | 109 | &rng_chrdev_ops, |
87 | }; | 110 | }; |
88 | 111 | ||
112 | static irqreturn_t random_interrupt(int irq, void *data) | ||
113 | { | ||
114 | wake_up(&host_read_wait); | ||
115 | |||
116 | return IRQ_HANDLED; | ||
117 | } | ||
118 | |||
89 | /* | 119 | /* |
90 | * rng_init - initialize RNG module | 120 | * rng_init - initialize RNG module |
91 | */ | 121 | */ |
@@ -93,28 +123,33 @@ static int __init rng_init (void) | |||
93 | { | 123 | { |
94 | int err; | 124 | int err; |
95 | 125 | ||
96 | err = os_open_file("/dev/random", of_read(OPENFLAGS()), 0); | 126 | err = os_open_file("/dev/random", of_read(OPENFLAGS()), 0); |
97 | if(err < 0) | 127 | if (err < 0) |
98 | goto out; | 128 | goto out; |
99 | 129 | ||
100 | random_fd = err; | 130 | random_fd = err; |
101 | 131 | ||
102 | err = os_set_fd_block(random_fd, 0); | 132 | err = um_request_irq(RANDOM_IRQ, random_fd, IRQ_READ, random_interrupt, |
103 | if(err) | 133 | IRQF_DISABLED | IRQF_SAMPLE_RANDOM, "random", |
134 | NULL); | ||
135 | if (err) | ||
104 | goto err_out_cleanup_hw; | 136 | goto err_out_cleanup_hw; |
105 | 137 | ||
138 | sigio_broken(random_fd, 1); | ||
139 | |||
106 | err = misc_register (&rng_miscdev); | 140 | err = misc_register (&rng_miscdev); |
107 | if (err) { | 141 | if (err) { |
108 | printk (KERN_ERR RNG_MODULE_NAME ": misc device register failed\n"); | 142 | printk (KERN_ERR RNG_MODULE_NAME ": misc device register " |
143 | "failed\n"); | ||
109 | goto err_out_cleanup_hw; | 144 | goto err_out_cleanup_hw; |
110 | } | 145 | } |
146 | out: | ||
147 | return err; | ||
111 | 148 | ||
112 | out: | 149 | err_out_cleanup_hw: |
113 | return err; | 150 | os_close_file(random_fd); |
114 | 151 | random_fd = -1; | |
115 | err_out_cleanup_hw: | 152 | goto out; |
116 | random_fd = -1; | ||
117 | goto out; | ||
118 | } | 153 | } |
119 | 154 | ||
120 | /* | 155 | /* |
@@ -122,6 +157,7 @@ static int __init rng_init (void) | |||
122 | */ | 157 | */ |
123 | static void __exit rng_cleanup (void) | 158 | static void __exit rng_cleanup (void) |
124 | { | 159 | { |
160 | os_close_file(random_fd); | ||
125 | misc_deregister (&rng_miscdev); | 161 | misc_deregister (&rng_miscdev); |
126 | } | 162 | } |
127 | 163 | ||
diff --git a/arch/um/drivers/slip_user.c b/arch/um/drivers/slip_user.c index 8b80505a3fb0..a1c2d2c98a94 100644 --- a/arch/um/drivers/slip_user.c +++ b/arch/um/drivers/slip_user.c | |||
@@ -96,7 +96,7 @@ static int slip_tramp(char **argv, int fd) | |||
96 | pid = err; | 96 | pid = err; |
97 | 97 | ||
98 | output_len = UM_KERN_PAGE_SIZE; | 98 | output_len = UM_KERN_PAGE_SIZE; |
99 | output = kmalloc(output_len, UM_GFP_KERNEL); | 99 | output = uml_kmalloc(output_len, UM_GFP_KERNEL); |
100 | if (output == NULL) { | 100 | if (output == NULL) { |
101 | printk(UM_KERN_ERR "slip_tramp : failed to allocate output " | 101 | printk(UM_KERN_ERR "slip_tramp : failed to allocate output " |
102 | "buffer\n"); | 102 | "buffer\n"); |
diff --git a/arch/um/drivers/tty.c b/arch/um/drivers/tty.c index c930fedc5172..495858a090e4 100644 --- a/arch/um/drivers/tty.c +++ b/arch/um/drivers/tty.c | |||
@@ -29,7 +29,7 @@ static void *tty_chan_init(char *str, int device, const struct chan_opts *opts) | |||
29 | } | 29 | } |
30 | str++; | 30 | str++; |
31 | 31 | ||
32 | data = kmalloc(sizeof(*data), UM_GFP_KERNEL); | 32 | data = uml_kmalloc(sizeof(*data), UM_GFP_KERNEL); |
33 | if (data == NULL) | 33 | if (data == NULL) |
34 | return NULL; | 34 | return NULL; |
35 | *data = ((struct tty_chan) { .dev = str, | 35 | *data = ((struct tty_chan) { .dev = str, |
diff --git a/arch/um/drivers/ubd_kern.c b/arch/um/drivers/ubd_kern.c index 5e45e39a8a8d..44ad1607be2d 100644 --- a/arch/um/drivers/ubd_kern.c +++ b/arch/um/drivers/ubd_kern.c | |||
@@ -1178,8 +1178,8 @@ static void cowify_bitmap(__u64 io_offset, int length, unsigned long *cow_mask, | |||
1178 | * by one word. Thanks to Lynn Kerby for the fix and James McMechan | 1178 | * by one word. Thanks to Lynn Kerby for the fix and James McMechan |
1179 | * for the original diagnosis. | 1179 | * for the original diagnosis. |
1180 | */ | 1180 | */ |
1181 | if(*cow_offset == ((bitmap_len + sizeof(unsigned long) - 1) / | 1181 | if (*cow_offset == (DIV_ROUND_UP(bitmap_len, |
1182 | sizeof(unsigned long) - 1)) | 1182 | sizeof(unsigned long)) - 1)) |
1183 | (*cow_offset)--; | 1183 | (*cow_offset)--; |
1184 | 1184 | ||
1185 | bitmap_words[0] = bitmap[*cow_offset]; | 1185 | bitmap_words[0] = bitmap[*cow_offset]; |
diff --git a/arch/um/drivers/xterm.c b/arch/um/drivers/xterm.c index 8a1c18a9b240..da2caa5a21ef 100644 --- a/arch/um/drivers/xterm.c +++ b/arch/um/drivers/xterm.c | |||
@@ -30,7 +30,7 @@ static void *xterm_init(char *str, int device, const struct chan_opts *opts) | |||
30 | { | 30 | { |
31 | struct xterm_chan *data; | 31 | struct xterm_chan *data; |
32 | 32 | ||
33 | data = kmalloc(sizeof(*data), UM_GFP_KERNEL); | 33 | data = uml_kmalloc(sizeof(*data), UM_GFP_KERNEL); |
34 | if (data == NULL) | 34 | if (data == NULL) |
35 | return NULL; | 35 | return NULL; |
36 | *data = ((struct xterm_chan) { .pid = -1, | 36 | *data = ((struct xterm_chan) { .pid = -1, |