Changeset View
Changeset View
Standalone View
Standalone View
head/sys/dev/vt/vt_core.c
Show First 20 Lines • Show All 107 Lines • ▼ Show 20 Lines | |||||
* really slows down the system. | * really slows down the system. | ||||
*/ | */ | ||||
#define VT_TIMERFREQ 25 | #define VT_TIMERFREQ 25 | ||||
/* Bell pitch/duration. */ | /* Bell pitch/duration. */ | ||||
#define VT_BELLDURATION ((5 * hz + 99) / 100) | #define VT_BELLDURATION ((5 * hz + 99) / 100) | ||||
#define VT_BELLPITCH 800 | #define VT_BELLPITCH 800 | ||||
#define VT_LOCK(vd) mtx_lock(&(vd)->vd_lock) | |||||
#define VT_UNLOCK(vd) mtx_unlock(&(vd)->vd_lock) | |||||
#define VT_LOCK_ASSERT(vd, what) mtx_assert(&(vd)->vd_lock, what) | |||||
#define VT_UNIT(vw) ((vw)->vw_device->vd_unit * VT_MAXWINDOWS + \ | #define VT_UNIT(vw) ((vw)->vw_device->vd_unit * VT_MAXWINDOWS + \ | ||||
(vw)->vw_number) | (vw)->vw_number) | ||||
static SYSCTL_NODE(_kern, OID_AUTO, vt, CTLFLAG_RD, 0, "vt(9) parameters"); | static SYSCTL_NODE(_kern, OID_AUTO, vt, CTLFLAG_RD, 0, "vt(9) parameters"); | ||||
static VT_SYSCTL_INT(enable_altgr, 1, "Enable AltGr key (Do not assume R.Alt as Alt)"); | static VT_SYSCTL_INT(enable_altgr, 1, "Enable AltGr key (Do not assume R.Alt as Alt)"); | ||||
static VT_SYSCTL_INT(enable_bell, 1, "Enable bell"); | static VT_SYSCTL_INT(enable_bell, 1, "Enable bell"); | ||||
static VT_SYSCTL_INT(debug, 0, "vt(9) debug level"); | static VT_SYSCTL_INT(debug, 0, "vt(9) debug level"); | ||||
static VT_SYSCTL_INT(deadtimer, 15, "Time to wait busy process in VT_PROCESS mode"); | static VT_SYSCTL_INT(deadtimer, 15, "Time to wait busy process in VT_PROCESS mode"); | ||||
static VT_SYSCTL_INT(suspendswitch, 1, "Switch to VT0 before suspend"); | static VT_SYSCTL_INT(suspendswitch, 1, "Switch to VT0 before suspend"); | ||||
/* Allow to disable some keyboard combinations. */ | /* Allow to disable some keyboard combinations. */ | ||||
static VT_SYSCTL_INT(kbd_halt, 1, "Enable halt keyboard combination. " | static VT_SYSCTL_INT(kbd_halt, 1, "Enable halt keyboard combination. " | ||||
"See kbdmap(5) to configure."); | "See kbdmap(5) to configure."); | ||||
static VT_SYSCTL_INT(kbd_poweroff, 1, "Enable Power Off keyboard combination. " | static VT_SYSCTL_INT(kbd_poweroff, 1, "Enable Power Off keyboard combination. " | ||||
"See kbdmap(5) to configure."); | "See kbdmap(5) to configure."); | ||||
static VT_SYSCTL_INT(kbd_reboot, 1, "Enable reboot keyboard combination. " | static VT_SYSCTL_INT(kbd_reboot, 1, "Enable reboot keyboard combination. " | ||||
"See kbdmap(5) to configure (typically Ctrl-Alt-Delete)."); | "See kbdmap(5) to configure (typically Ctrl-Alt-Delete)."); | ||||
static VT_SYSCTL_INT(kbd_debug, 1, "Enable key combination to enter debugger. " | static VT_SYSCTL_INT(kbd_debug, 1, "Enable key combination to enter debugger. " | ||||
"See kbdmap(5) to configure (typically Ctrl-Alt-Esc)."); | "See kbdmap(5) to configure (typically Ctrl-Alt-Esc)."); | ||||
static VT_SYSCTL_INT(kbd_panic, 0, "Enable request to panic. " | static VT_SYSCTL_INT(kbd_panic, 0, "Enable request to panic. " | ||||
"See kbdmap(5) to configure."); | "See kbdmap(5) to configure."); | ||||
/* Used internally, not a tunable. */ | |||||
int vt_draw_logo_cpus; | |||||
VT_SYSCTL_INT(splash_cpu, 1, "Show logo CPUs during boot"); | |||||
VT_SYSCTL_INT(splash_ncpu, 0, "Override number of logos displayed " | |||||
"(0 = do not override)"); | |||||
VT_SYSCTL_INT(splash_cpu_style, 1, "Draw logo style " | |||||
"(0=Beastie, 1=Alternate beastie, 2=Orb)"); | |||||
VT_SYSCTL_INT(splash_cpu_duration, 10, "Hide logos after (seconds)"); | |||||
static struct vt_device vt_consdev; | static struct vt_device vt_consdev; | ||||
static unsigned int vt_unit = 0; | static unsigned int vt_unit = 0; | ||||
static MALLOC_DEFINE(M_VT, "vt", "vt device"); | static MALLOC_DEFINE(M_VT, "vt", "vt device"); | ||||
struct vt_device *main_vd = &vt_consdev; | struct vt_device *main_vd = &vt_consdev; | ||||
/* Boot logo. */ | /* Boot logo. */ | ||||
extern unsigned int vt_logo_width; | extern unsigned int vt_logo_width; | ||||
extern unsigned int vt_logo_height; | extern unsigned int vt_logo_height; | ||||
Show All 21 Lines | |||||
static void vt_suspend_handler(void *priv); | static void vt_suspend_handler(void *priv); | ||||
static void vt_resume_handler(void *priv); | static void vt_resume_handler(void *priv); | ||||
SET_DECLARE(vt_drv_set, struct vt_driver); | SET_DECLARE(vt_drv_set, struct vt_driver); | ||||
#define _VTDEFH MAX(100, PIXEL_HEIGHT(VT_FB_DEFAULT_HEIGHT)) | #define _VTDEFH MAX(100, PIXEL_HEIGHT(VT_FB_DEFAULT_HEIGHT)) | ||||
#define _VTDEFW MAX(200, PIXEL_WIDTH(VT_FB_DEFAULT_WIDTH)) | #define _VTDEFW MAX(200, PIXEL_WIDTH(VT_FB_DEFAULT_WIDTH)) | ||||
static struct terminal vt_consterm; | struct terminal vt_consterm; | ||||
static struct vt_window vt_conswindow; | static struct vt_window vt_conswindow; | ||||
static struct vt_device vt_consdev = { | static struct vt_device vt_consdev = { | ||||
.vd_driver = NULL, | .vd_driver = NULL, | ||||
.vd_softc = NULL, | .vd_softc = NULL, | ||||
.vd_prev_driver = NULL, | .vd_prev_driver = NULL, | ||||
.vd_prev_softc = NULL, | .vd_prev_softc = NULL, | ||||
.vd_flags = VDF_INVALID, | .vd_flags = VDF_INVALID, | ||||
.vd_windows = { [VT_CONSWINDOW] = &vt_conswindow, }, | .vd_windows = { [VT_CONSWINDOW] = &vt_conswindow, }, | ||||
Show All 30 Lines | .vb_scr_size = { | ||||
.tp_col = _VTDEFW, | .tp_col = _VTDEFW, | ||||
}, | }, | ||||
}, | }, | ||||
.vw_device = &vt_consdev, | .vw_device = &vt_consdev, | ||||
.vw_terminal = &vt_consterm, | .vw_terminal = &vt_consterm, | ||||
.vw_kbdmode = K_XLATE, | .vw_kbdmode = K_XLATE, | ||||
.vw_grabbed = 0, | .vw_grabbed = 0, | ||||
}; | }; | ||||
static struct terminal vt_consterm = { | struct terminal vt_consterm = { | ||||
.tm_class = &vt_termclass, | .tm_class = &vt_termclass, | ||||
.tm_softc = &vt_conswindow, | .tm_softc = &vt_conswindow, | ||||
.tm_flags = TF_CONS, | .tm_flags = TF_CONS, | ||||
}; | }; | ||||
static struct consdev vt_consterm_consdev = { | static struct consdev vt_consterm_consdev = { | ||||
.cn_ops = &termcn_cnops, | .cn_ops = &termcn_cnops, | ||||
.cn_arg = &vt_consterm, | .cn_arg = &vt_consterm, | ||||
.cn_name = "ttyv0", | .cn_name = "ttyv0", | ||||
Show All 35 Lines | vt_schedule_flush(struct vt_device *vd, int ms) | ||||
if (ms <= 0) | if (ms <= 0) | ||||
/* Default to initial value. */ | /* Default to initial value. */ | ||||
ms = 1000 / VT_TIMERFREQ; | ms = 1000 / VT_TIMERFREQ; | ||||
callout_schedule(&vd->vd_timer, hz / (1000 / ms)); | callout_schedule(&vd->vd_timer, hz / (1000 / ms)); | ||||
} | } | ||||
static void | void | ||||
vt_resume_flush_timer(struct vt_device *vd, int ms) | vt_resume_flush_timer(struct vt_device *vd, int ms) | ||||
{ | { | ||||
if (!(vd->vd_flags & VDF_ASYNC) || | if (!(vd->vd_flags & VDF_ASYNC) || | ||||
!atomic_cmpset_int(&vd->vd_timer_armed, 0, 1)) | !atomic_cmpset_int(&vd->vd_timer_armed, 0, 1)) | ||||
return; | return; | ||||
vt_schedule_flush(vd, ms); | vt_schedule_flush(vd, ms); | ||||
▲ Show 20 Lines • Show All 256 Lines • ▼ Show 20 Lines | if (kbd != NULL) { | ||||
vt_update_kbd_state(vw, kbd); | vt_update_kbd_state(vw, kbd); | ||||
} | } | ||||
mtx_unlock(&Giant); | mtx_unlock(&Giant); | ||||
DPRINTF(10, "%s(ttyv%d) done\n", __func__, vw->vw_number); | DPRINTF(10, "%s(ttyv%d) done\n", __func__, vw->vw_number); | ||||
return (0); | return (0); | ||||
} | } | ||||
static inline void | void | ||||
vt_termsize(struct vt_device *vd, struct vt_font *vf, term_pos_t *size) | vt_termsize(struct vt_device *vd, struct vt_font *vf, term_pos_t *size) | ||||
{ | { | ||||
size->tp_row = vd->vd_height; | size->tp_row = vd->vd_height; | ||||
if (vt_draw_logo_cpus) | |||||
size->tp_row -= vt_logo_sprite_height; | |||||
size->tp_col = vd->vd_width; | size->tp_col = vd->vd_width; | ||||
if (vf != NULL) { | if (vf != NULL) { | ||||
size->tp_row /= vf->vf_height; | size->tp_row /= vf->vf_height; | ||||
size->tp_col /= vf->vf_width; | size->tp_col /= vf->vf_width; | ||||
} | } | ||||
} | } | ||||
static inline void | static inline void | ||||
vt_termrect(struct vt_device *vd, struct vt_font *vf, term_rect_t *rect) | |||||
{ | |||||
rect->tr_begin.tp_row = rect->tr_begin.tp_col = 0; | |||||
if (vt_draw_logo_cpus) | |||||
rect->tr_begin.tp_row = vt_logo_sprite_height; | |||||
rect->tr_end.tp_row = vd->vd_height; | |||||
rect->tr_end.tp_col = vd->vd_width; | |||||
if (vf != NULL) { | |||||
rect->tr_begin.tp_row = | |||||
howmany(rect->tr_begin.tp_row, vf->vf_height); | |||||
rect->tr_end.tp_row /= vf->vf_height; | |||||
rect->tr_end.tp_col /= vf->vf_width; | |||||
} | |||||
} | |||||
void | |||||
vt_winsize(struct vt_device *vd, struct vt_font *vf, struct winsize *size) | vt_winsize(struct vt_device *vd, struct vt_font *vf, struct winsize *size) | ||||
{ | { | ||||
size->ws_row = size->ws_ypixel = vd->vd_height; | size->ws_ypixel = vd->vd_height; | ||||
if (vt_draw_logo_cpus) | |||||
size->ws_ypixel -= vt_logo_sprite_height; | |||||
size->ws_row = size->ws_ypixel; | |||||
size->ws_col = size->ws_xpixel = vd->vd_width; | size->ws_col = size->ws_xpixel = vd->vd_width; | ||||
if (vf != NULL) { | if (vf != NULL) { | ||||
size->ws_row /= vf->vf_height; | size->ws_row /= vf->vf_height; | ||||
size->ws_col /= vf->vf_width; | size->ws_col /= vf->vf_width; | ||||
} | } | ||||
} | } | ||||
static inline void | void | ||||
vt_compute_drawable_area(struct vt_window *vw) | vt_compute_drawable_area(struct vt_window *vw) | ||||
{ | { | ||||
struct vt_device *vd; | struct vt_device *vd; | ||||
struct vt_font *vf; | struct vt_font *vf; | ||||
vt_axis_t height; | |||||
vd = vw->vw_device; | vd = vw->vw_device; | ||||
if (vw->vw_font == NULL) { | if (vw->vw_font == NULL) { | ||||
vw->vw_draw_area.tr_begin.tp_col = 0; | vw->vw_draw_area.tr_begin.tp_col = 0; | ||||
vw->vw_draw_area.tr_begin.tp_row = 0; | vw->vw_draw_area.tr_begin.tp_row = 0; | ||||
if (vt_draw_logo_cpus) | |||||
vw->vw_draw_area.tr_begin.tp_row = vt_logo_sprite_height; | |||||
vw->vw_draw_area.tr_end.tp_col = vd->vd_width; | vw->vw_draw_area.tr_end.tp_col = vd->vd_width; | ||||
vw->vw_draw_area.tr_end.tp_row = vd->vd_height; | vw->vw_draw_area.tr_end.tp_row = vd->vd_height; | ||||
return; | return; | ||||
} | } | ||||
vf = vw->vw_font; | vf = vw->vw_font; | ||||
/* | /* | ||||
* Compute the drawable area, so that the text is centered on | * Compute the drawable area, so that the text is centered on | ||||
* the screen. | * the screen. | ||||
*/ | */ | ||||
height = vd->vd_height; | |||||
if (vt_draw_logo_cpus) | |||||
height -= vt_logo_sprite_height; | |||||
vw->vw_draw_area.tr_begin.tp_col = (vd->vd_width % vf->vf_width) / 2; | vw->vw_draw_area.tr_begin.tp_col = (vd->vd_width % vf->vf_width) / 2; | ||||
vw->vw_draw_area.tr_begin.tp_row = (vd->vd_height % vf->vf_height) / 2; | vw->vw_draw_area.tr_begin.tp_row = (height % vf->vf_height) / 2; | ||||
if (vt_draw_logo_cpus) | |||||
vw->vw_draw_area.tr_begin.tp_row += vt_logo_sprite_height; | |||||
vw->vw_draw_area.tr_end.tp_col = vw->vw_draw_area.tr_begin.tp_col + | vw->vw_draw_area.tr_end.tp_col = vw->vw_draw_area.tr_begin.tp_col + | ||||
vd->vd_width / vf->vf_width * vf->vf_width; | vd->vd_width / vf->vf_width * vf->vf_width; | ||||
vw->vw_draw_area.tr_end.tp_row = vw->vw_draw_area.tr_begin.tp_row + | vw->vw_draw_area.tr_end.tp_row = vw->vw_draw_area.tr_begin.tp_row + | ||||
vd->vd_height / vf->vf_height * vf->vf_height; | height / vf->vf_height * vf->vf_height; | ||||
} | } | ||||
static void | static void | ||||
vt_scroll(struct vt_window *vw, int offset, int whence) | vt_scroll(struct vt_window *vw, int offset, int whence) | ||||
{ | { | ||||
int diff; | int diff; | ||||
term_pos_t size; | term_pos_t size; | ||||
▲ Show 20 Lines • Show All 494 Lines • ▼ Show 20 Lines | |||||
#endif | #endif | ||||
static int | static int | ||||
vt_flush(struct vt_device *vd) | vt_flush(struct vt_device *vd) | ||||
{ | { | ||||
struct vt_window *vw; | struct vt_window *vw; | ||||
struct vt_font *vf; | struct vt_font *vf; | ||||
term_rect_t tarea; | term_rect_t tarea; | ||||
term_pos_t size; | |||||
#ifndef SC_NO_CUTPASTE | #ifndef SC_NO_CUTPASTE | ||||
int cursor_was_shown, cursor_moved; | int cursor_was_shown, cursor_moved; | ||||
#endif | #endif | ||||
vw = vd->vd_curwindow; | vw = vd->vd_curwindow; | ||||
if (vw == NULL) | if (vw == NULL) | ||||
return (0); | return (0); | ||||
Show All 38 Lines | #ifndef SC_NO_CUTPASTE | ||||
* If the cursor is displayed and has moved since last refresh, | * If the cursor is displayed and has moved since last refresh, | ||||
* mark the new position as dirty. | * mark the new position as dirty. | ||||
*/ | */ | ||||
if (vd->vd_mshown && cursor_moved) | if (vd->vd_mshown && cursor_moved) | ||||
vt_mark_mouse_position_as_dirty(vd); | vt_mark_mouse_position_as_dirty(vd); | ||||
#endif | #endif | ||||
vtbuf_undirty(&vw->vw_buf, &tarea); | vtbuf_undirty(&vw->vw_buf, &tarea); | ||||
vt_termsize(vd, vf, &size); | |||||
/* Force a full redraw when the screen contents are invalid. */ | /* Force a full redraw when the screen contents are invalid. */ | ||||
if (vd->vd_flags & VDF_INVALID) { | if (vd->vd_flags & VDF_INVALID) { | ||||
tarea.tr_begin.tp_row = tarea.tr_begin.tp_col = 0; | |||||
tarea.tr_end = size; | |||||
vd->vd_flags &= ~VDF_INVALID; | vd->vd_flags &= ~VDF_INVALID; | ||||
vt_termrect(vd, vf, &tarea); | |||||
if (vt_draw_logo_cpus) | |||||
vtterm_draw_cpu_logos(vd); | |||||
} | } | ||||
if (tarea.tr_begin.tp_col < tarea.tr_end.tp_col) { | if (tarea.tr_begin.tp_col < tarea.tr_end.tp_col) { | ||||
vd->vd_driver->vd_bitblt_text(vd, vw, &tarea); | vd->vd_driver->vd_bitblt_text(vd, vw, &tarea); | ||||
return (1); | return (1); | ||||
} | } | ||||
return (0); | return (0); | ||||
▲ Show 20 Lines • Show All 128 Lines • ▼ Show 20 Lines | c = (boothowto & RB_MUTE) == 0 ? TERMINAL_KERN_ATTR : | ||||
TERMINAL_NORM_ATTR; | TERMINAL_NORM_ATTR; | ||||
attr.ta_format = TCHAR_FORMAT(c); | attr.ta_format = TCHAR_FORMAT(c); | ||||
attr.ta_fgcolor = TCHAR_FGCOLOR(c); | attr.ta_fgcolor = TCHAR_FGCOLOR(c); | ||||
attr.ta_bgcolor = TCHAR_BGCOLOR(c); | attr.ta_bgcolor = TCHAR_BGCOLOR(c); | ||||
terminal_set_winsize_blank(tm, &wsz, 1, &attr); | terminal_set_winsize_blank(tm, &wsz, 1, &attr); | ||||
if (vtdbest != NULL) { | if (vtdbest != NULL) { | ||||
#ifdef DEV_SPLASH | #ifdef DEV_SPLASH | ||||
if (!vt_splash_cpu) | |||||
vtterm_splash(vd); | vtterm_splash(vd); | ||||
#endif | #endif | ||||
vd->vd_flags |= VDF_INITIALIZED; | vd->vd_flags |= VDF_INITIALIZED; | ||||
} | } | ||||
} | } | ||||
static int | static int | ||||
vtterm_cngetc(struct terminal *tm) | vtterm_cngetc(struct terminal *tm) | ||||
{ | { | ||||
▲ Show 20 Lines • Show All 1,472 Lines • Show Last 20 Lines |