aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/char
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/char')
-rw-r--r--drivers/char/efirtc.c1
-rw-r--r--drivers/char/hvc_iucv.c2
-rw-r--r--drivers/char/ipmi/ipmi_kcs_sm.c2
-rw-r--r--drivers/char/keyboard.c10
-rw-r--r--drivers/char/mem.c161
-rw-r--r--drivers/char/misc.c26
-rw-r--r--drivers/char/random.c10
-rw-r--r--drivers/char/sysrq.c2
-rw-r--r--drivers/char/vt.c50
9 files changed, 126 insertions, 138 deletions
diff --git a/drivers/char/efirtc.c b/drivers/char/efirtc.c
index 26a47dc88f61..53c524e7b829 100644
--- a/drivers/char/efirtc.c
+++ b/drivers/char/efirtc.c
@@ -285,6 +285,7 @@ static const struct file_operations efi_rtc_fops = {
285 .unlocked_ioctl = efi_rtc_ioctl, 285 .unlocked_ioctl = efi_rtc_ioctl,
286 .open = efi_rtc_open, 286 .open = efi_rtc_open,
287 .release = efi_rtc_close, 287 .release = efi_rtc_close,
288 .llseek = no_llseek,
288}; 289};
289 290
290static struct miscdevice efi_rtc_dev= { 291static struct miscdevice efi_rtc_dev= {
diff --git a/drivers/char/hvc_iucv.c b/drivers/char/hvc_iucv.c
index b8a5d654d3d0..fe62bd0e17b7 100644
--- a/drivers/char/hvc_iucv.c
+++ b/drivers/char/hvc_iucv.c
@@ -931,7 +931,7 @@ static struct hv_ops hvc_iucv_ops = {
931}; 931};
932 932
933/* Suspend / resume device operations */ 933/* Suspend / resume device operations */
934static struct dev_pm_ops hvc_iucv_pm_ops = { 934static const struct dev_pm_ops hvc_iucv_pm_ops = {
935 .freeze = hvc_iucv_pm_freeze, 935 .freeze = hvc_iucv_pm_freeze,
936 .thaw = hvc_iucv_pm_restore_thaw, 936 .thaw = hvc_iucv_pm_restore_thaw,
937 .restore = hvc_iucv_pm_restore_thaw, 937 .restore = hvc_iucv_pm_restore_thaw,
diff --git a/drivers/char/ipmi/ipmi_kcs_sm.c b/drivers/char/ipmi/ipmi_kcs_sm.c
index 80704875794c..cf82fedae099 100644
--- a/drivers/char/ipmi/ipmi_kcs_sm.c
+++ b/drivers/char/ipmi/ipmi_kcs_sm.c
@@ -370,7 +370,7 @@ static enum si_sm_result kcs_event(struct si_sm_data *kcs, long time)
370 return SI_SM_IDLE; 370 return SI_SM_IDLE;
371 371
372 case KCS_START_OP: 372 case KCS_START_OP:
373 if (state != KCS_IDLE) { 373 if (state != KCS_IDLE_STATE) {
374 start_error_recovery(kcs, 374 start_error_recovery(kcs,
375 "State machine not idle at start"); 375 "State machine not idle at start");
376 break; 376 break;
diff --git a/drivers/char/keyboard.c b/drivers/char/keyboard.c
index 5619007e7e05..f706b1dffdb3 100644
--- a/drivers/char/keyboard.c
+++ b/drivers/char/keyboard.c
@@ -233,7 +233,8 @@ int setkeycode(unsigned int scancode, unsigned int keycode)
233} 233}
234 234
235/* 235/*
236 * Making beeps and bells. 236 * Making beeps and bells. Note that we prefer beeps to bells, but when
237 * shutting the sound off we do both.
237 */ 238 */
238 239
239static int kd_sound_helper(struct input_handle *handle, void *data) 240static int kd_sound_helper(struct input_handle *handle, void *data)
@@ -242,9 +243,12 @@ static int kd_sound_helper(struct input_handle *handle, void *data)
242 struct input_dev *dev = handle->dev; 243 struct input_dev *dev = handle->dev;
243 244
244 if (test_bit(EV_SND, dev->evbit)) { 245 if (test_bit(EV_SND, dev->evbit)) {
245 if (test_bit(SND_TONE, dev->sndbit)) 246 if (test_bit(SND_TONE, dev->sndbit)) {
246 input_inject_event(handle, EV_SND, SND_TONE, *hz); 247 input_inject_event(handle, EV_SND, SND_TONE, *hz);
247 if (test_bit(SND_BELL, handle->dev->sndbit)) 248 if (*hz)
249 return 0;
250 }
251 if (test_bit(SND_BELL, dev->sndbit))
248 input_inject_event(handle, EV_SND, SND_BELL, *hz ? 1 : 0); 252 input_inject_event(handle, EV_SND, SND_BELL, *hz ? 1 : 0);
249 } 253 }
250 254
diff --git a/drivers/char/mem.c b/drivers/char/mem.c
index fba76fb55abf..be832b6f8279 100644
--- a/drivers/char/mem.c
+++ b/drivers/char/mem.c
@@ -34,6 +34,16 @@
34# include <linux/efi.h> 34# include <linux/efi.h>
35#endif 35#endif
36 36
37static inline unsigned long size_inside_page(unsigned long start,
38 unsigned long size)
39{
40 unsigned long sz;
41
42 sz = PAGE_SIZE - (start & (PAGE_SIZE - 1));
43
44 return min(sz, size);
45}
46
37/* 47/*
38 * Architectures vary in how they handle caching for addresses 48 * Architectures vary in how they handle caching for addresses
39 * outside of main memory. 49 * outside of main memory.
@@ -126,9 +136,7 @@ static ssize_t read_mem(struct file * file, char __user * buf,
126#ifdef __ARCH_HAS_NO_PAGE_ZERO_MAPPED 136#ifdef __ARCH_HAS_NO_PAGE_ZERO_MAPPED
127 /* we don't have page 0 mapped on sparc and m68k.. */ 137 /* we don't have page 0 mapped on sparc and m68k.. */
128 if (p < PAGE_SIZE) { 138 if (p < PAGE_SIZE) {
129 sz = PAGE_SIZE - p; 139 sz = size_inside_page(p, count);
130 if (sz > count)
131 sz = count;
132 if (sz > 0) { 140 if (sz > 0) {
133 if (clear_user(buf, sz)) 141 if (clear_user(buf, sz))
134 return -EFAULT; 142 return -EFAULT;
@@ -141,15 +149,9 @@ static ssize_t read_mem(struct file * file, char __user * buf,
141#endif 149#endif
142 150
143 while (count > 0) { 151 while (count > 0) {
144 /* 152 unsigned long remaining;
145 * Handle first page in case it's not aligned
146 */
147 if (-p & (PAGE_SIZE - 1))
148 sz = -p & (PAGE_SIZE - 1);
149 else
150 sz = PAGE_SIZE;
151 153
152 sz = min_t(unsigned long, sz, count); 154 sz = size_inside_page(p, count);
153 155
154 if (!range_is_allowed(p >> PAGE_SHIFT, count)) 156 if (!range_is_allowed(p >> PAGE_SHIFT, count))
155 return -EPERM; 157 return -EPERM;
@@ -163,12 +165,10 @@ static ssize_t read_mem(struct file * file, char __user * buf,
163 if (!ptr) 165 if (!ptr)
164 return -EFAULT; 166 return -EFAULT;
165 167
166 if (copy_to_user(buf, ptr, sz)) { 168 remaining = copy_to_user(buf, ptr, sz);
167 unxlate_dev_mem_ptr(p, ptr);
168 return -EFAULT;
169 }
170
171 unxlate_dev_mem_ptr(p, ptr); 169 unxlate_dev_mem_ptr(p, ptr);
170 if (remaining)
171 return -EFAULT;
172 172
173 buf += sz; 173 buf += sz;
174 p += sz; 174 p += sz;
@@ -196,9 +196,7 @@ static ssize_t write_mem(struct file * file, const char __user * buf,
196#ifdef __ARCH_HAS_NO_PAGE_ZERO_MAPPED 196#ifdef __ARCH_HAS_NO_PAGE_ZERO_MAPPED
197 /* we don't have page 0 mapped on sparc and m68k.. */ 197 /* we don't have page 0 mapped on sparc and m68k.. */
198 if (p < PAGE_SIZE) { 198 if (p < PAGE_SIZE) {
199 unsigned long sz = PAGE_SIZE - p; 199 sz = size_inside_page(p, count);
200 if (sz > count)
201 sz = count;
202 /* Hmm. Do something? */ 200 /* Hmm. Do something? */
203 buf += sz; 201 buf += sz;
204 p += sz; 202 p += sz;
@@ -208,15 +206,7 @@ static ssize_t write_mem(struct file * file, const char __user * buf,
208#endif 206#endif
209 207
210 while (count > 0) { 208 while (count > 0) {
211 /* 209 sz = size_inside_page(p, count);
212 * Handle first page in case it's not aligned
213 */
214 if (-p & (PAGE_SIZE - 1))
215 sz = -p & (PAGE_SIZE - 1);
216 else
217 sz = PAGE_SIZE;
218
219 sz = min_t(unsigned long, sz, count);
220 210
221 if (!range_is_allowed(p >> PAGE_SHIFT, sz)) 211 if (!range_is_allowed(p >> PAGE_SHIFT, sz))
222 return -EPERM; 212 return -EPERM;
@@ -234,16 +224,14 @@ static ssize_t write_mem(struct file * file, const char __user * buf,
234 } 224 }
235 225
236 copied = copy_from_user(ptr, buf, sz); 226 copied = copy_from_user(ptr, buf, sz);
227 unxlate_dev_mem_ptr(p, ptr);
237 if (copied) { 228 if (copied) {
238 written += sz - copied; 229 written += sz - copied;
239 unxlate_dev_mem_ptr(p, ptr);
240 if (written) 230 if (written)
241 break; 231 break;
242 return -EFAULT; 232 return -EFAULT;
243 } 233 }
244 234
245 unxlate_dev_mem_ptr(p, ptr);
246
247 buf += sz; 235 buf += sz;
248 p += sz; 236 p += sz;
249 count -= sz; 237 count -= sz;
@@ -417,27 +405,18 @@ static ssize_t read_kmem(struct file *file, char __user *buf,
417#ifdef __ARCH_HAS_NO_PAGE_ZERO_MAPPED 405#ifdef __ARCH_HAS_NO_PAGE_ZERO_MAPPED
418 /* we don't have page 0 mapped on sparc and m68k.. */ 406 /* we don't have page 0 mapped on sparc and m68k.. */
419 if (p < PAGE_SIZE && low_count > 0) { 407 if (p < PAGE_SIZE && low_count > 0) {
420 size_t tmp = PAGE_SIZE - p; 408 sz = size_inside_page(p, low_count);
421 if (tmp > low_count) tmp = low_count; 409 if (clear_user(buf, sz))
422 if (clear_user(buf, tmp))
423 return -EFAULT; 410 return -EFAULT;
424 buf += tmp; 411 buf += sz;
425 p += tmp; 412 p += sz;
426 read += tmp; 413 read += sz;
427 low_count -= tmp; 414 low_count -= sz;
428 count -= tmp; 415 count -= sz;
429 } 416 }
430#endif 417#endif
431 while (low_count > 0) { 418 while (low_count > 0) {
432 /* 419 sz = size_inside_page(p, low_count);
433 * Handle first page in case it's not aligned
434 */
435 if (-p & (PAGE_SIZE - 1))
436 sz = -p & (PAGE_SIZE - 1);
437 else
438 sz = PAGE_SIZE;
439
440 sz = min_t(unsigned long, sz, low_count);
441 420
442 /* 421 /*
443 * On ia64 if a page has been mapped somewhere as 422 * On ia64 if a page has been mapped somewhere as
@@ -461,21 +440,18 @@ static ssize_t read_kmem(struct file *file, char __user *buf,
461 if (!kbuf) 440 if (!kbuf)
462 return -ENOMEM; 441 return -ENOMEM;
463 while (count > 0) { 442 while (count > 0) {
464 int len = count; 443 sz = size_inside_page(p, count);
465 444 sz = vread(kbuf, (char *)p, sz);
466 if (len > PAGE_SIZE) 445 if (!sz)
467 len = PAGE_SIZE;
468 len = vread(kbuf, (char *)p, len);
469 if (!len)
470 break; 446 break;
471 if (copy_to_user(buf, kbuf, len)) { 447 if (copy_to_user(buf, kbuf, sz)) {
472 free_page((unsigned long)kbuf); 448 free_page((unsigned long)kbuf);
473 return -EFAULT; 449 return -EFAULT;
474 } 450 }
475 count -= len; 451 count -= sz;
476 buf += len; 452 buf += sz;
477 read += len; 453 read += sz;
478 p += len; 454 p += sz;
479 } 455 }
480 free_page((unsigned long)kbuf); 456 free_page((unsigned long)kbuf);
481 } 457 }
@@ -485,7 +461,7 @@ static ssize_t read_kmem(struct file *file, char __user *buf,
485 461
486 462
487static inline ssize_t 463static inline ssize_t
488do_write_kmem(void *p, unsigned long realp, const char __user * buf, 464do_write_kmem(unsigned long p, const char __user *buf,
489 size_t count, loff_t *ppos) 465 size_t count, loff_t *ppos)
490{ 466{
491 ssize_t written, sz; 467 ssize_t written, sz;
@@ -494,14 +470,11 @@ do_write_kmem(void *p, unsigned long realp, const char __user * buf,
494 written = 0; 470 written = 0;
495#ifdef __ARCH_HAS_NO_PAGE_ZERO_MAPPED 471#ifdef __ARCH_HAS_NO_PAGE_ZERO_MAPPED
496 /* we don't have page 0 mapped on sparc and m68k.. */ 472 /* we don't have page 0 mapped on sparc and m68k.. */
497 if (realp < PAGE_SIZE) { 473 if (p < PAGE_SIZE) {
498 unsigned long sz = PAGE_SIZE - realp; 474 sz = size_inside_page(p, count);
499 if (sz > count)
500 sz = count;
501 /* Hmm. Do something? */ 475 /* Hmm. Do something? */
502 buf += sz; 476 buf += sz;
503 p += sz; 477 p += sz;
504 realp += sz;
505 count -= sz; 478 count -= sz;
506 written += sz; 479 written += sz;
507 } 480 }
@@ -509,22 +482,15 @@ do_write_kmem(void *p, unsigned long realp, const char __user * buf,
509 482
510 while (count > 0) { 483 while (count > 0) {
511 char *ptr; 484 char *ptr;
512 /*
513 * Handle first page in case it's not aligned
514 */
515 if (-realp & (PAGE_SIZE - 1))
516 sz = -realp & (PAGE_SIZE - 1);
517 else
518 sz = PAGE_SIZE;
519 485
520 sz = min_t(unsigned long, sz, count); 486 sz = size_inside_page(p, count);
521 487
522 /* 488 /*
523 * On ia64 if a page has been mapped somewhere as 489 * On ia64 if a page has been mapped somewhere as
524 * uncached, then it must also be accessed uncached 490 * uncached, then it must also be accessed uncached
525 * by the kernel or data corruption may occur 491 * by the kernel or data corruption may occur
526 */ 492 */
527 ptr = xlate_dev_kmem_ptr(p); 493 ptr = xlate_dev_kmem_ptr((char *)p);
528 494
529 copied = copy_from_user(ptr, buf, sz); 495 copied = copy_from_user(ptr, buf, sz);
530 if (copied) { 496 if (copied) {
@@ -535,7 +501,6 @@ do_write_kmem(void *p, unsigned long realp, const char __user * buf,
535 } 501 }
536 buf += sz; 502 buf += sz;
537 p += sz; 503 p += sz;
538 realp += sz;
539 count -= sz; 504 count -= sz;
540 written += sz; 505 written += sz;
541 } 506 }
@@ -554,19 +519,14 @@ static ssize_t write_kmem(struct file * file, const char __user * buf,
554 unsigned long p = *ppos; 519 unsigned long p = *ppos;
555 ssize_t wrote = 0; 520 ssize_t wrote = 0;
556 ssize_t virtr = 0; 521 ssize_t virtr = 0;
557 ssize_t written;
558 char * kbuf; /* k-addr because vwrite() takes vmlist_lock rwlock */ 522 char * kbuf; /* k-addr because vwrite() takes vmlist_lock rwlock */
559 523
560 if (p < (unsigned long) high_memory) { 524 if (p < (unsigned long) high_memory) {
561 525 unsigned long to_write = min_t(unsigned long, count,
562 wrote = count; 526 (unsigned long)high_memory - p);
563 if (count > (unsigned long) high_memory - p) 527 wrote = do_write_kmem(p, buf, to_write, ppos);
564 wrote = (unsigned long) high_memory - p; 528 if (wrote != to_write)
565 529 return wrote;
566 written = do_write_kmem((void*)p, p, buf, wrote, ppos);
567 if (written != wrote)
568 return written;
569 wrote = written;
570 p += wrote; 530 p += wrote;
571 buf += wrote; 531 buf += wrote;
572 count -= wrote; 532 count -= wrote;
@@ -577,24 +537,21 @@ static ssize_t write_kmem(struct file * file, const char __user * buf,
577 if (!kbuf) 537 if (!kbuf)
578 return wrote ? wrote : -ENOMEM; 538 return wrote ? wrote : -ENOMEM;
579 while (count > 0) { 539 while (count > 0) {
580 int len = count; 540 unsigned long sz = size_inside_page(p, count);
581 541 unsigned long n;
582 if (len > PAGE_SIZE) 542
583 len = PAGE_SIZE; 543 n = copy_from_user(kbuf, buf, sz);
584 if (len) { 544 if (n) {
585 written = copy_from_user(kbuf, buf, len); 545 if (wrote + virtr)
586 if (written) { 546 break;
587 if (wrote + virtr) 547 free_page((unsigned long)kbuf);
588 break; 548 return -EFAULT;
589 free_page((unsigned long)kbuf);
590 return -EFAULT;
591 }
592 } 549 }
593 len = vwrite(kbuf, (char *)p, len); 550 sz = vwrite(kbuf, (char *)p, sz);
594 count -= len; 551 count -= sz;
595 buf += len; 552 buf += sz;
596 virtr += len; 553 virtr += sz;
597 p += len; 554 p += sz;
598 } 555 }
599 free_page((unsigned long)kbuf); 556 free_page((unsigned long)kbuf);
600 } 557 }
diff --git a/drivers/char/misc.c b/drivers/char/misc.c
index 96f1cd086dd2..94a136e96c06 100644
--- a/drivers/char/misc.c
+++ b/drivers/char/misc.c
@@ -60,9 +60,7 @@ static DEFINE_MUTEX(misc_mtx);
60 * Assigned numbers, used for dynamic minors 60 * Assigned numbers, used for dynamic minors
61 */ 61 */
62#define DYNAMIC_MINORS 64 /* like dynamic majors */ 62#define DYNAMIC_MINORS 64 /* like dynamic majors */
63static unsigned char misc_minors[DYNAMIC_MINORS / 8]; 63static DECLARE_BITMAP(misc_minors, DYNAMIC_MINORS);
64
65extern int pmu_device_init(void);
66 64
67#ifdef CONFIG_PROC_FS 65#ifdef CONFIG_PROC_FS
68static void *misc_seq_start(struct seq_file *seq, loff_t *pos) 66static void *misc_seq_start(struct seq_file *seq, loff_t *pos)
@@ -198,24 +196,23 @@ int misc_register(struct miscdevice * misc)
198 } 196 }
199 197
200 if (misc->minor == MISC_DYNAMIC_MINOR) { 198 if (misc->minor == MISC_DYNAMIC_MINOR) {
201 int i = DYNAMIC_MINORS; 199 int i = find_first_zero_bit(misc_minors, DYNAMIC_MINORS);
202 while (--i >= 0) 200 if (i >= DYNAMIC_MINORS) {
203 if ( (misc_minors[i>>3] & (1 << (i&7))) == 0)
204 break;
205 if (i<0) {
206 mutex_unlock(&misc_mtx); 201 mutex_unlock(&misc_mtx);
207 return -EBUSY; 202 return -EBUSY;
208 } 203 }
209 misc->minor = i; 204 misc->minor = DYNAMIC_MINORS - i - 1;
205 set_bit(i, misc_minors);
210 } 206 }
211 207
212 if (misc->minor < DYNAMIC_MINORS)
213 misc_minors[misc->minor >> 3] |= 1 << (misc->minor & 7);
214 dev = MKDEV(MISC_MAJOR, misc->minor); 208 dev = MKDEV(MISC_MAJOR, misc->minor);
215 209
216 misc->this_device = device_create(misc_class, misc->parent, dev, 210 misc->this_device = device_create(misc_class, misc->parent, dev,
217 misc, "%s", misc->name); 211 misc, "%s", misc->name);
218 if (IS_ERR(misc->this_device)) { 212 if (IS_ERR(misc->this_device)) {
213 int i = DYNAMIC_MINORS - misc->minor - 1;
214 if (i < DYNAMIC_MINORS && i >= 0)
215 clear_bit(i, misc_minors);
219 err = PTR_ERR(misc->this_device); 216 err = PTR_ERR(misc->this_device);
220 goto out; 217 goto out;
221 } 218 }
@@ -242,7 +239,7 @@ int misc_register(struct miscdevice * misc)
242 239
243int misc_deregister(struct miscdevice *misc) 240int misc_deregister(struct miscdevice *misc)
244{ 241{
245 int i = misc->minor; 242 int i = DYNAMIC_MINORS - misc->minor - 1;
246 243
247 if (list_empty(&misc->list)) 244 if (list_empty(&misc->list))
248 return -EINVAL; 245 return -EINVAL;
@@ -250,9 +247,8 @@ int misc_deregister(struct miscdevice *misc)
250 mutex_lock(&misc_mtx); 247 mutex_lock(&misc_mtx);
251 list_del(&misc->list); 248 list_del(&misc->list);
252 device_destroy(misc_class, MKDEV(MISC_MAJOR, misc->minor)); 249 device_destroy(misc_class, MKDEV(MISC_MAJOR, misc->minor));
253 if (i < DYNAMIC_MINORS && i>0) { 250 if (i < DYNAMIC_MINORS && i >= 0)
254 misc_minors[i>>3] &= ~(1 << (misc->minor & 7)); 251 clear_bit(i, misc_minors);
255 }
256 mutex_unlock(&misc_mtx); 252 mutex_unlock(&misc_mtx);
257 return 0; 253 return 0;
258} 254}
diff --git a/drivers/char/random.c b/drivers/char/random.c
index dcd08635cf1b..8258982b49ec 100644
--- a/drivers/char/random.c
+++ b/drivers/char/random.c
@@ -1245,12 +1245,8 @@ static int proc_do_uuid(ctl_table *table, int write,
1245 if (uuid[8] == 0) 1245 if (uuid[8] == 0)
1246 generate_random_uuid(uuid); 1246 generate_random_uuid(uuid);
1247 1247
1248 sprintf(buf, "%02x%02x%02x%02x-%02x%02x-%02x%02x-%02x%02x-" 1248 sprintf(buf, "%pU", uuid);
1249 "%02x%02x%02x%02x%02x%02x", 1249
1250 uuid[0], uuid[1], uuid[2], uuid[3],
1251 uuid[4], uuid[5], uuid[6], uuid[7],
1252 uuid[8], uuid[9], uuid[10], uuid[11],
1253 uuid[12], uuid[13], uuid[14], uuid[15]);
1254 fake_table.data = buf; 1250 fake_table.data = buf;
1255 fake_table.maxlen = sizeof(buf); 1251 fake_table.maxlen = sizeof(buf);
1256 1252
@@ -1310,7 +1306,7 @@ ctl_table random_table[] = {
1310 1306
1311/******************************************************************** 1307/********************************************************************
1312 * 1308 *
1313 * Random funtions for networking 1309 * Random functions for networking
1314 * 1310 *
1315 ********************************************************************/ 1311 ********************************************************************/
1316 1312
diff --git a/drivers/char/sysrq.c b/drivers/char/sysrq.c
index 44203ff599da..1ae2de7d8b4f 100644
--- a/drivers/char/sysrq.c
+++ b/drivers/char/sysrq.c
@@ -339,7 +339,7 @@ static struct sysrq_key_op sysrq_term_op = {
339 339
340static void moom_callback(struct work_struct *ignored) 340static void moom_callback(struct work_struct *ignored)
341{ 341{
342 out_of_memory(node_zonelist(0, GFP_KERNEL), GFP_KERNEL, 0); 342 out_of_memory(node_zonelist(0, GFP_KERNEL), GFP_KERNEL, 0, NULL);
343} 343}
344 344
345static DECLARE_WORK(moom_work, moom_callback); 345static DECLARE_WORK(moom_work, moom_callback);
diff --git a/drivers/char/vt.c b/drivers/char/vt.c
index 1e3d728dbf7e..50faa1fb0f06 100644
--- a/drivers/char/vt.c
+++ b/drivers/char/vt.c
@@ -164,6 +164,9 @@ module_param(default_utf8, int, S_IRUGO | S_IWUSR);
164int global_cursor_default = -1; 164int global_cursor_default = -1;
165module_param(global_cursor_default, int, S_IRUGO | S_IWUSR); 165module_param(global_cursor_default, int, S_IRUGO | S_IWUSR);
166 166
167static int cur_default = CUR_DEFAULT;
168module_param(cur_default, int, S_IRUGO | S_IWUSR);
169
167/* 170/*
168 * ignore_poke: don't unblank the screen when things are typed. This is 171 * ignore_poke: don't unblank the screen when things are typed. This is
169 * mainly for the privacy of braille terminal users. 172 * mainly for the privacy of braille terminal users.
@@ -184,12 +187,10 @@ static DECLARE_WORK(console_work, console_callback);
184 * fg_console is the current virtual console, 187 * fg_console is the current virtual console,
185 * last_console is the last used one, 188 * last_console is the last used one,
186 * want_console is the console we want to switch to, 189 * want_console is the console we want to switch to,
187 * kmsg_redirect is the console for kernel messages,
188 */ 190 */
189int fg_console; 191int fg_console;
190int last_console; 192int last_console;
191int want_console = -1; 193int want_console = -1;
192int kmsg_redirect;
193 194
194/* 195/*
195 * For each existing display, we have a pointer to console currently visible 196 * For each existing display, we have a pointer to console currently visible
@@ -1638,7 +1639,7 @@ static void reset_terminal(struct vc_data *vc, int do_clear)
1638 /* do not do set_leds here because this causes an endless tasklet loop 1639 /* do not do set_leds here because this causes an endless tasklet loop
1639 when the keyboard hasn't been initialized yet */ 1640 when the keyboard hasn't been initialized yet */
1640 1641
1641 vc->vc_cursor_type = CUR_DEFAULT; 1642 vc->vc_cursor_type = cur_default;
1642 vc->vc_complement_mask = vc->vc_s_complement_mask; 1643 vc->vc_complement_mask = vc->vc_s_complement_mask;
1643 1644
1644 default_attr(vc); 1645 default_attr(vc);
@@ -1840,7 +1841,7 @@ static void do_con_trol(struct tty_struct *tty, struct vc_data *vc, int c)
1840 if (vc->vc_par[0]) 1841 if (vc->vc_par[0])
1841 vc->vc_cursor_type = vc->vc_par[0] | (vc->vc_par[1] << 8) | (vc->vc_par[2] << 16); 1842 vc->vc_cursor_type = vc->vc_par[0] | (vc->vc_par[1] << 8) | (vc->vc_par[2] << 16);
1842 else 1843 else
1843 vc->vc_cursor_type = CUR_DEFAULT; 1844 vc->vc_cursor_type = cur_default;
1844 return; 1845 return;
1845 } 1846 }
1846 break; 1847 break;
@@ -2434,6 +2435,37 @@ struct tty_driver *console_driver;
2434 2435
2435#ifdef CONFIG_VT_CONSOLE 2436#ifdef CONFIG_VT_CONSOLE
2436 2437
2438/**
2439 * vt_kmsg_redirect() - Sets/gets the kernel message console
2440 * @new: The new virtual terminal number or -1 if the console should stay
2441 * unchanged
2442 *
2443 * By default, the kernel messages are always printed on the current virtual
2444 * console. However, the user may modify that default with the
2445 * TIOCL_SETKMSGREDIRECT ioctl call.
2446 *
2447 * This function sets the kernel message console to be @new. It returns the old
2448 * virtual console number. The virtual terminal number 0 (both as parameter and
2449 * return value) means no redirection (i.e. always printed on the currently
2450 * active console).
2451 *
2452 * The parameter -1 means that only the current console is returned, but the
2453 * value is not modified. You may use the macro vt_get_kmsg_redirect() in that
2454 * case to make the code more understandable.
2455 *
2456 * When the kernel is compiled without CONFIG_VT_CONSOLE, this function ignores
2457 * the parameter and always returns 0.
2458 */
2459int vt_kmsg_redirect(int new)
2460{
2461 static int kmsg_con;
2462
2463 if (new != -1)
2464 return xchg(&kmsg_con, new);
2465 else
2466 return kmsg_con;
2467}
2468
2437/* 2469/*
2438 * Console on virtual terminal 2470 * Console on virtual terminal
2439 * 2471 *
@@ -2448,6 +2480,7 @@ static void vt_console_print(struct console *co, const char *b, unsigned count)
2448 const ushort *start; 2480 const ushort *start;
2449 ushort cnt = 0; 2481 ushort cnt = 0;
2450 ushort myx; 2482 ushort myx;
2483 int kmsg_console;
2451 2484
2452 /* console busy or not yet initialized */ 2485 /* console busy or not yet initialized */
2453 if (!printable) 2486 if (!printable)
@@ -2455,8 +2488,9 @@ static void vt_console_print(struct console *co, const char *b, unsigned count)
2455 if (!spin_trylock(&printing_lock)) 2488 if (!spin_trylock(&printing_lock))
2456 return; 2489 return;
2457 2490
2458 if (kmsg_redirect && vc_cons_allocated(kmsg_redirect - 1)) 2491 kmsg_console = vt_get_kmsg_redirect();
2459 vc = vc_cons[kmsg_redirect - 1].d; 2492 if (kmsg_console && vc_cons_allocated(kmsg_console - 1))
2493 vc = vc_cons[kmsg_console - 1].d;
2460 2494
2461 /* read `x' only after setting currcons properly (otherwise 2495 /* read `x' only after setting currcons properly (otherwise
2462 the `x' macro will read the x of the foreground console). */ 2496 the `x' macro will read the x of the foreground console). */
@@ -2613,7 +2647,7 @@ int tioclinux(struct tty_struct *tty, unsigned long arg)
2613 ret = set_vesa_blanking(p); 2647 ret = set_vesa_blanking(p);
2614 break; 2648 break;
2615 case TIOCL_GETKMSGREDIRECT: 2649 case TIOCL_GETKMSGREDIRECT:
2616 data = kmsg_redirect; 2650 data = vt_get_kmsg_redirect();
2617 ret = __put_user(data, p); 2651 ret = __put_user(data, p);
2618 break; 2652 break;
2619 case TIOCL_SETKMSGREDIRECT: 2653 case TIOCL_SETKMSGREDIRECT:
@@ -2623,7 +2657,7 @@ int tioclinux(struct tty_struct *tty, unsigned long arg)
2623 if (get_user(data, p+1)) 2657 if (get_user(data, p+1))
2624 ret = -EFAULT; 2658 ret = -EFAULT;
2625 else 2659 else
2626 kmsg_redirect = data; 2660 vt_kmsg_redirect(data);
2627 } 2661 }
2628 break; 2662 break;
2629 case TIOCL_GETFGCONSOLE: 2663 case TIOCL_GETFGCONSOLE: