From: <jsi...@us...> - 2007-07-16 15:52:27
|
Revision: 2382 http://linuxconsole.svn.sourceforge.net/linuxconsole/?rev=2382&view=rev Author: jsimmons Date: 2007-07-16 08:52:23 -0700 (Mon, 16 Jul 2007) Log Message: ----------- Some changes to vga con causes a lock up. Will find later Modified Paths: -------------- branches/ruby-2.6.21/ruby-2.6/drivers/video/console/vgacon.c Modified: branches/ruby-2.6.21/ruby-2.6/drivers/video/console/vgacon.c =================================================================== --- branches/ruby-2.6.21/ruby-2.6/drivers/video/console/vgacon.c 2007-07-16 15:51:42 UTC (rev 2381) +++ branches/ruby-2.6.21/ruby-2.6/drivers/video/console/vgacon.c 2007-07-16 15:52:23 UTC (rev 2382) @@ -47,10 +47,6 @@ #include <linux/init.h> #include <linux/screen_info.h> #include <linux/smp_lock.h> -#ifdef CONFIG_IA64 -#include <linux/efi.h> -#endif - #include <video/vga.h> #include <asm/io.h> @@ -60,6 +56,8 @@ static int cursor_size_lastfrom; static int cursor_size_lastto; +static u32 vgacon_xres; +static u32 vgacon_yres; static struct vgastate state; #define BLANK 0x0020 @@ -73,7 +71,7 @@ * appear. */ #undef TRIDENT_GLITCH - +#define VGA_FONTWIDTH 8 /* VGA does not support fontwidths != 8 */ /* * Interface used by the world */ @@ -89,7 +87,7 @@ static int vgacon_set_origin(struct vc_data *c); static void vgacon_save_screen(struct vc_data *c); static int vgacon_scroll_region(struct vc_data *c, int t, int b, int dir, - int lines); + int lines); static u8 vgacon_build_attr(struct vc_data *c, u8 color, u8 intensity, u8 blink, u8 underline, u8 reverse); static void vgacon_invert_region(struct vc_data *c, u16 * p, int count); @@ -102,6 +100,10 @@ static unsigned int vga_vram_size __read_mostly; /* Size of video memory */ static u16 vga_video_port_reg __read_mostly; /* Video register select port */ static u16 vga_video_port_val __read_mostly; /* Video register value port */ +static unsigned int vga_video_num_columns; /* Number of text columns */ +static unsigned int vga_video_num_lines; /* Number of text lines */ +static int vga_can_do_color __read_mostly; /* Do we support colors? */ +static unsigned int vga_default_font_height __read_mostly; /* Height of default screen font */ static unsigned char vga_video_type __read_mostly; /* Card type */ static unsigned char vga_hardscroll_enabled __read_mostly; static unsigned char vga_hardscroll_user_enable __read_mostly = 1; @@ -110,6 +112,8 @@ static int vga_palette_blanked; static int vga_is_gfx; static int vga_512_chars; +static int vga_video_font_height; +static int vga_scan_lines __read_mostly; static unsigned int vga_rolled_over; static int __init no_scroll(char *str) @@ -354,21 +358,15 @@ static const char *vgacon_startup(struct vt_struct *vt, int init) { - struct vc_data *vc = &vga_default; + struct vc_data *vc = vt->default_mode = &vga_default; const char *display_desc = NULL; u16 saved1, saved2; volatile u16 *p; -#ifdef CONFIG_IA64 - if (efi_mem_type(0xA0000) == EFI_CONVENTIONAL_MEMORY) - goto no_vga: -#endif - if (ORIG_VIDEO_ISVGA == VIDEO_TYPE_VLFB) { no_vga: return NULL; } - vt->default_mode = vc; /* VGA16 modes are not handled by VGACON */ if ((ORIG_VIDEO_MODE == 0x0D) || /* 320x200/4 */ @@ -378,8 +376,8 @@ (ORIG_VIDEO_MODE == 0x6A)) /* 800x600/4, 0x6A is very common */ goto no_vga; - vc->vc_rows = ORIG_VIDEO_LINES; - vc->vc_cols = ORIG_VIDEO_COLS; + vc->vc_rows = vga_video_num_lines = ORIG_VIDEO_LINES; + vc->vc_cols = vga_video_num_columns = ORIG_VIDEO_COLS; state.vgabase = NULL; if (ORIG_VIDEO_MODE == 7) { /* Is this a monochrome display? */ @@ -406,11 +404,11 @@ &mda1_console_resource); request_resource(&ioport_resource, &mda2_console_resource); - vc->vc_font.height = 14; + vc->vc_font.height = vga_video_font_height = 14; } } else { /* If not, it is color. */ - vc->vc_can_do_color = 1; + vc->vc_can_do_color = vga_can_do_color = 1; vga_vram_base = 0xb8000; vga_video_port_reg = VGA_CRT_IC; vga_video_port_val = VGA_CRT_DC; @@ -478,7 +476,7 @@ display_desc = "*CGA"; request_resource(&ioport_resource, &cga_console_resource); - vc->vc_font.height = 8; + vc->vc_font.height = vga_video_font_height = 8; } } @@ -513,11 +511,18 @@ || vga_video_type == VIDEO_TYPE_VGAC || vga_video_type == VIDEO_TYPE_EGAM) { vga_hardscroll_enabled = vga_hardscroll_user_enable; - vc->vc_font.height = ORIG_VIDEO_POINTS; + vga_default_font_height = ORIG_VIDEO_POINTS; + vga_video_font_height = ORIG_VIDEO_POINTS; /* This may be suboptimal but is a safe bet - go with it */ - vc->vc_scan_lines = vc->vc_font.height * vc->vc_rows; + vga_scan_lines = + vga_video_font_height * vga_video_num_lines; + vc->vc_font.height = vga_default_font_height; + vc->vc_scan_lines = vga_scan_lines; } + vgacon_xres = ORIG_VIDEO_COLS * VGA_FONTWIDTH; + vgacon_yres = vga_scan_lines; + if (!vga_init_done) { vgacon_scrollback_startup(); vga_init_done = 1; @@ -528,7 +533,6 @@ static void vgacon_init(struct vc_data *c, int init) { - struct vc_data *default_mode = c->display_fg->default_mode; unsigned long p; /* @@ -536,14 +540,17 @@ * but vgacon_init can be called more than once, and init will * not be 1. */ - c->vc_can_do_color = default_mode->vc_can_do_color; - + c->vc_can_do_color = vga_can_do_color; + /* set dimensions manually if init != 0 since vc_resize() will fail */ - c->vc_cols = default_mode->vc_cols; - c->vc_rows = default_mode->vc_rows; + if (init) { + c->vc_cols = vga_video_num_columns; + c->vc_rows = vga_video_num_lines; + } else + vc_resize(c, vga_video_num_columns, vga_video_num_lines); - c->vc_scan_lines = default_mode->vc_scan_lines; - c->vc_font.height = default_mode->vc_font.height; + c->vc_scan_lines = vga_scan_lines; + c->vc_font.height = vga_video_font_height; c->vc_complement_mask = 0x7700; if (vga_512_chars) c->vc_hi_font_mask = 0x0800; @@ -574,7 +581,7 @@ { u8 attr = color; - if (c->vc_can_do_color) { + if (vga_can_do_color) { if (underline) attr = (attr & 0xf0) | c->vc_ulcolor; else if (intensity == 0) @@ -588,7 +595,7 @@ attr ^= 0x80; if (intensity == 2) attr ^= 0x08; - if (!c->vc_can_do_color) { + if (!vga_can_do_color) { if (underline) attr = (attr & 0xf8) | 0x01; else if (intensity == 0) @@ -599,7 +606,7 @@ static void vgacon_invert_region(struct vc_data *c, u16 * p, int count) { - int col = c->vc_can_do_color; + int col = vga_can_do_color; while (count--) { u16 a = scr_readw(p); @@ -655,7 +662,7 @@ switch (mode) { case CM_ERASE: write_vga(14, (c->vc_pos - vga_vram_base) / 2); - if (vga_video_type >= VIDEO_TYPE_VGAC) + if (vga_video_type >= VIDEO_TYPE_VGAC) vgacon_set_cursor_size(c->vc_x, 31, 30); else vgacon_set_cursor_size(c->vc_x, 31, 31); @@ -719,6 +726,8 @@ spin_lock_irqsave(&vga_lock, flags); + vgacon_xres = width * VGA_FONTWIDTH; + vgacon_yres = height * c->vc_font.height; if (vga_video_type >= VIDEO_TYPE_VGAC) { outb_p(VGA_CRTC_MAX_SCAN, vga_video_port_reg); max_scan = inb_p(vga_video_port_val); @@ -772,23 +781,30 @@ static int vgacon_switch(struct vc_data *c) { + int x = c->vc_cols * VGA_FONTWIDTH; int y = c->vc_rows * c->vc_font.height; - int x = c->vc_cols = 8; + int rows = ORIG_VIDEO_LINES * vga_default_font_height/ + c->vc_font.height; + /* + * We need to save screen size here as it's the only way + * we can spot the screen has been resized and we need to + * set size of freshly allocated screens ourselves. + */ + vga_video_num_columns = c->vc_cols; + vga_video_num_lines = c->vc_rows; /* We can only copy out the size of the video buffer here, - * otherwise we get into VGA BIOS. We can only copy out - * the size of the video buffer here, otherwise we get - * into VGA BIOS */ + * otherwise we get into VGA BIOS */ if (!vga_is_gfx) { - struct winsize *ws = &c->vc_tty->winsize; - scr_memcpyw((u16 *) c->vc_origin, (u16 *) c->vc_screenbuf, c->vc_screenbuf_size > vga_vram_size ? vga_vram_size : c->vc_screenbuf_size); - if ((ws->ws_xpixel != x || ws->ws_ypixel != y) && - (!(c->vc_cols % 2) && c->vc_cols <= ORIG_VIDEO_COLS)) + if ((vgacon_xres != x || vgacon_yres != y) && + (!(vga_video_num_columns % 2) && + vga_video_num_columns <= ORIG_VIDEO_COLS && + vga_video_num_lines <= rows)) vgacon_doresize(c, c->vc_cols, c->vc_rows); } @@ -812,7 +828,8 @@ static int vgacon_set_palette(struct vc_data *vc, unsigned char *table) { #ifdef CAN_LOAD_PALETTE - if (vga_video_type != VIDEO_TYPE_VGAC || vga_palette_blanked) + if (vga_video_type != VIDEO_TYPE_VGAC || vga_palette_blanked + || !IS_VISIBLE) return -EINVAL; vga_set_palette(vc, table); return 0; @@ -1125,7 +1142,6 @@ /* attribute controller */ for (i = 0; i < vga_vt.vc_count; i++) { struct vc_data *vc = vga_vt.vc_cons[i]; - if (vc) vc->vc_hi_font_mask = ch512 ? 0x0800 : 0; } @@ -1151,13 +1167,8 @@ static int vgacon_adjust_height(struct vc_data *vc, unsigned fontheight) { unsigned char ovr, vde, fsr; - int rows, maxscan; + int rows, maxscan, i; - if (fontheight == vc->vc_font.height) - return 0; - - vc->vc_font.height = fontheight; - rows = vc->vc_scan_lines / fontheight; /* Number of video rows we end up with */ maxscan = rows * fontheight - 1; /* Scan lines to actually display-1 */ @@ -1191,14 +1202,21 @@ outb_p(0x12, vga_video_port_reg); /* Vertical display limit */ outb_p(vde, vga_video_port_val); spin_unlock_irq(&vga_lock); + vga_video_font_height = fontheight; - if (IS_VISIBLE) { - /* void size to cause regs to be rewritten */ - cursor_size_lastfrom = 0; - cursor_size_lastto = 0; - vgacon_cursor(vc, CM_DRAW); - vc->vc_font.height = fontheight; - vc_resize(vc, 0, rows); /* Adjust console size */ + for (i = 0; i < vga_vt.vc_count; i++) { + struct vc_data *vc = vga_vt.vc_cons[i]; + + if (vc) { + if (IS_VISIBLE) { + /* void size to cause regs to be rewritten */ + cursor_size_lastfrom = 0; + cursor_size_lastto = 0; + vc->display_fg->vt_sw->con_cursor(vc, CM_DRAW); + } + vc->vc_font.height = fontheight; + vc_resize(vc, 0, rows); /* Adjust console size */ + } } return 0; } @@ -1211,7 +1229,8 @@ if (vga_video_type < VIDEO_TYPE_EGAM) return -EINVAL; - if (font->width != 8 || (charcount != 256 && charcount != 512)) + if (font->width != VGA_FONTWIDTH || + (charcount != 256 && charcount != 512)) return -EINVAL; rc = vgacon_do_font_op(&state, font->data, 1, charcount == 512); @@ -1228,7 +1247,7 @@ if (vga_video_type < VIDEO_TYPE_EGAM) return -EINVAL; - font->width = 8; + font->width = VGA_FONTWIDTH; font->height = c->vc_font.height; font->charcount = vga_512_chars ? 512 : 256; if (!font->data) @@ -1247,7 +1266,7 @@ unsigned int height) { if (width % 2 || width > ORIG_VIDEO_COLS || - height > (ORIG_VIDEO_LINES * vc->vc_font.height)/ + height > (ORIG_VIDEO_LINES * vga_default_font_height)/ vc->vc_font.height) /* let svgatextmode tinker with video timings */ return 0; @@ -1260,7 +1279,7 @@ static int vgacon_set_origin(struct vc_data *c) { if (vga_is_gfx || /* We don't play origin tricks in graphic modes */ - (c->display_fg->vt_blanked && !vga_palette_blanked)) /* Nor we write to blanked screens */ + (c->display_fg->vt_blanked && !vga_palette_blanked))/* Nor we write to blanked screens */ return 0; c->vc_origin = c->vc_visible_origin = vga_vram_base; vga_set_mem_top(c); @@ -1270,6 +1289,18 @@ static void vgacon_save_screen(struct vc_data *c) { + static int vga_bootup_console = 0; + + if (!vga_bootup_console) { + /* This is a gross hack, but here is the only place we can + * set bootup console parameters without messing up generic + * console initialization routines. + */ + vga_bootup_console = 1; + c->vc_x = ORIG_X; + c->vc_y = ORIG_Y; + } + /* We can't copy in more then the size of the video buffer, * or we'll be copying in VGA BIOS */ @@ -1279,7 +1310,7 @@ } static int vgacon_scroll_region(struct vc_data *c, int t, int b, int dir, - int lines) + int lines) { unsigned long oldo; unsigned int delta; @@ -1370,7 +1401,7 @@ memset(&vga_vt, 0, sizeof(struct vt_struct)); vga_vt.kmalloced = 0; vga_vt.vt_sw = &vga_con; - display_desc = vt_map_display(&vga_vt, 1, MAX_NR_USER_CONSOLES); + display_desc = vt_map_display(&vga_vt, 1, 16); if (!display_desc) return -ENODEV; printk("Console: %s %s %dx%d vc:%d-%d\n", vga_vt.default_mode->vc_can_do_color ? "Colour" : "Mono", @@ -1378,6 +1409,6 @@ vga_vt.default_mode->vc_rows, vga_vt.first_vc + 1, vga_vt.first_vc + vga_vt.vc_count); return 0; -} +} MODULE_LICENSE("GPL"); This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |