aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/video
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/video')
-rw-r--r--drivers/video/console/fbcon.c92
-rw-r--r--drivers/video/console/fbcon.h3
2 files changed, 52 insertions, 43 deletions
diff --git a/drivers/video/console/fbcon.c b/drivers/video/console/fbcon.c
index bb4ea50b54a3..2e93224d2d55 100644
--- a/drivers/video/console/fbcon.c
+++ b/drivers/video/console/fbcon.c
@@ -331,6 +331,35 @@ static void cursor_timer_handler(unsigned long dev_addr)
331 mod_timer(&ops->cursor_timer, jiffies + HZ/5); 331 mod_timer(&ops->cursor_timer, jiffies + HZ/5);
332} 332}
333 333
334static void fbcon_add_cursor_timer(struct fb_info *info)
335{
336 struct fbcon_ops *ops = info->fbcon_par;
337
338 if ((!info->queue.func || info->queue.func == fb_flashcursor) &&
339 !(ops->flags & FBCON_FLAGS_CURSOR_TIMER)) {
340 if (!info->queue.func)
341 INIT_WORK(&info->queue, fb_flashcursor, info);
342
343 init_timer(&ops->cursor_timer);
344 ops->cursor_timer.function = cursor_timer_handler;
345 ops->cursor_timer.expires = jiffies + HZ / 5;
346 ops->cursor_timer.data = (unsigned long ) info;
347 add_timer(&ops->cursor_timer);
348 ops->flags |= FBCON_FLAGS_CURSOR_TIMER;
349 }
350}
351
352static void fbcon_del_cursor_timer(struct fb_info *info)
353{
354 struct fbcon_ops *ops = info->fbcon_par;
355
356 if (info->queue.func == fb_flashcursor &&
357 ops->flags & FBCON_FLAGS_CURSOR_TIMER) {
358 del_timer_sync(&ops->cursor_timer);
359 ops->flags &= ~FBCON_FLAGS_CURSOR_TIMER;
360 }
361}
362
334#ifndef MODULE 363#ifndef MODULE
335static int __init fb_console_setup(char *this_opt) 364static int __init fb_console_setup(char *this_opt)
336{ 365{
@@ -583,9 +612,7 @@ static int con2fb_release_oldinfo(struct vc_data *vc, struct fb_info *oldinfo,
583 } 612 }
584 613
585 if (!err) { 614 if (!err) {
586 if (oldinfo->queue.func == fb_flashcursor) 615 fbcon_del_cursor_timer(oldinfo);
587 del_timer_sync(&ops->cursor_timer);
588
589 kfree(ops->cursor_state.mask); 616 kfree(ops->cursor_state.mask);
590 kfree(ops->cursor_data); 617 kfree(ops->cursor_data);
591 kfree(oldinfo->fbcon_par); 618 kfree(oldinfo->fbcon_par);
@@ -596,22 +623,6 @@ static int con2fb_release_oldinfo(struct vc_data *vc, struct fb_info *oldinfo,
596 return err; 623 return err;
597} 624}
598 625
599static void con2fb_init_newinfo(struct fb_info *info)
600{
601 if (!info->queue.func || info->queue.func == fb_flashcursor) {
602 struct fbcon_ops *ops = info->fbcon_par;
603
604 if (!info->queue.func)
605 INIT_WORK(&info->queue, fb_flashcursor, info);
606
607 init_timer(&ops->cursor_timer);
608 ops->cursor_timer.function = cursor_timer_handler;
609 ops->cursor_timer.expires = jiffies + HZ / 5;
610 ops->cursor_timer.data = (unsigned long ) info;
611 add_timer(&ops->cursor_timer);
612 }
613}
614
615static void con2fb_init_display(struct vc_data *vc, struct fb_info *info, 626static void con2fb_init_display(struct vc_data *vc, struct fb_info *info,
616 int unit, int show_logo) 627 int unit, int show_logo)
617{ 628{
@@ -695,7 +706,7 @@ static int set_con2fb_map(int unit, int newidx, int user)
695 logo_shown != FBCON_LOGO_DONTSHOW); 706 logo_shown != FBCON_LOGO_DONTSHOW);
696 707
697 if (!found) 708 if (!found)
698 con2fb_init_newinfo(info); 709 fbcon_add_cursor_timer(info);
699 con2fb_map_boot[unit] = newidx; 710 con2fb_map_boot[unit] = newidx;
700 con2fb_init_display(vc, info, unit, show_logo); 711 con2fb_init_display(vc, info, unit, show_logo);
701 } 712 }
@@ -898,18 +909,7 @@ static const char *fbcon_startup(void)
898 } 909 }
899#endif /* CONFIG_MAC */ 910#endif /* CONFIG_MAC */
900 911
901 /* Initialize the work queue. If the driver provides its 912 fbcon_add_cursor_timer(info);
902 * own work queue this means it will use something besides
903 * default timer to flash the cursor. */
904 if (!info->queue.func) {
905 INIT_WORK(&info->queue, fb_flashcursor, info);
906
907 init_timer(&ops->cursor_timer);
908 ops->cursor_timer.function = cursor_timer_handler;
909 ops->cursor_timer.expires = jiffies + HZ / 5;
910 ops->cursor_timer.data = (unsigned long ) info;
911 add_timer(&ops->cursor_timer);
912 }
913 return display_desc; 913 return display_desc;
914} 914}
915 915
@@ -1923,7 +1923,7 @@ static int fbcon_resize(struct vc_data *vc, unsigned int width,
1923 1923
1924static int fbcon_switch(struct vc_data *vc) 1924static int fbcon_switch(struct vc_data *vc)
1925{ 1925{
1926 struct fb_info *info; 1926 struct fb_info *info, *old_info = NULL;
1927 struct display *p = &fb_display[vc->vc_num]; 1927 struct display *p = &fb_display[vc->vc_num];
1928 struct fb_var_screeninfo var; 1928 struct fb_var_screeninfo var;
1929 int i, prev_console; 1929 int i, prev_console;
@@ -1956,7 +1956,8 @@ static int fbcon_switch(struct vc_data *vc)
1956 } 1956 }
1957 1957
1958 prev_console = ((struct fbcon_ops *)info->fbcon_par)->currcon; 1958 prev_console = ((struct fbcon_ops *)info->fbcon_par)->currcon;
1959 1959 if (prev_console != -1)
1960 old_info = registered_fb[con2fb_map[prev_console]];
1960 /* 1961 /*
1961 * FIXME: If we have multiple fbdev's loaded, we need to 1962 * FIXME: If we have multiple fbdev's loaded, we need to
1962 * update all info->currcon. Perhaps, we can place this 1963 * update all info->currcon. Perhaps, we can place this
@@ -1984,10 +1985,12 @@ static int fbcon_switch(struct vc_data *vc)
1984 info->var.yoffset = info->var.xoffset = p->yscroll = 0; 1985 info->var.yoffset = info->var.xoffset = p->yscroll = 0;
1985 fb_set_var(info, &var); 1986 fb_set_var(info, &var);
1986 1987
1987 if (prev_console != -1 && 1988 if (old_info != NULL && old_info != info) {
1988 registered_fb[con2fb_map[prev_console]] != info && 1989 if (info->fbops->fb_set_par)
1989 info->fbops->fb_set_par) 1990 info->fbops->fb_set_par(info);
1990 info->fbops->fb_set_par(info); 1991 fbcon_del_cursor_timer(old_info);
1992 fbcon_add_cursor_timer(info);
1993 }
1991 1994
1992 set_blitting_type(vc, info, p); 1995 set_blitting_type(vc, info, p);
1993 ((struct fbcon_ops *)info->fbcon_par)->cursor_reset = 1; 1996 ((struct fbcon_ops *)info->fbcon_par)->cursor_reset = 1;
@@ -2073,11 +2076,16 @@ static int fbcon_blank(struct vc_data *vc, int blank, int mode_switch)
2073 fbcon_generic_blank(vc, info, blank); 2076 fbcon_generic_blank(vc, info, blank);
2074 } 2077 }
2075 2078
2076 if (!blank) 2079 if (!blank)
2077 update_screen(vc); 2080 update_screen(vc);
2078 } 2081 }
2082
2083 if (!blank)
2084 fbcon_add_cursor_timer(info);
2085 else
2086 fbcon_del_cursor_timer(info);
2079 2087
2080 return 0; 2088 return 0;
2081} 2089}
2082 2090
2083static void fbcon_free_font(struct display *p) 2091static void fbcon_free_font(struct display *p)
diff --git a/drivers/video/console/fbcon.h b/drivers/video/console/fbcon.h
index 5d377860bce2..08befafe11d1 100644
--- a/drivers/video/console/fbcon.h
+++ b/drivers/video/console/fbcon.h
@@ -18,7 +18,8 @@
18 18
19#include <asm/io.h> 19#include <asm/io.h>
20 20
21#define FBCON_FLAGS_INIT 1 21#define FBCON_FLAGS_INIT 1
22#define FBCON_FLAGS_CURSOR_TIMER 2
22 23
23 /* 24 /*
24 * This is the interface between the low-level console driver and the 25 * This is the interface between the low-level console driver and the