Commit 77aa6cbf authored by Christoph Hellwig's avatar Christoph Hellwig Committed by Linus Torvalds

[PATCH] cleanup virtual console <-> selection.c interface

Pass around pointers instead of indices into a global array between various
files of the virtual console implementation and stop using obsfucting
macros that expect certain variables to be in scope.

This is a first step to get rid of the various global arrays in the VC
code.
Signed-off-by: default avatarAndrew Morton <akpm@osdl.org>
Signed-off-by: default avatarLinus Torvalds <torvalds@osdl.org>
parent cd3ae7b3
...@@ -33,7 +33,7 @@ extern void poke_blanked_console(void); ...@@ -33,7 +33,7 @@ extern void poke_blanked_console(void);
/* Variables for selection control. */ /* Variables for selection control. */
/* Use a dynamic buffer, instead of static (Dec 1994) */ /* Use a dynamic buffer, instead of static (Dec 1994) */
int sel_cons; /* must not be disallocated */ struct vc_data *sel_cons; /* must not be disallocated */
static volatile int sel_start = -1; /* cleared by clear_selection */ static volatile int sel_start = -1; /* cleared by clear_selection */
static int sel_end; static int sel_end;
static int sel_buffer_lth; static int sel_buffer_lth;
...@@ -44,20 +44,22 @@ static char *sel_buffer; ...@@ -44,20 +44,22 @@ static char *sel_buffer;
/* set reverse video on characters s-e of console with selection. */ /* set reverse video on characters s-e of console with selection. */
inline static void inline static void
highlight(const int s, const int e) { highlight(const int s, const int e)
{
invert_screen(sel_cons, s, e-s+2, 1); invert_screen(sel_cons, s, e-s+2, 1);
} }
/* use complementary color to show the pointer */ /* use complementary color to show the pointer */
inline static void inline static void
highlight_pointer(const int where) { highlight_pointer(const int where)
{
complement_pos(sel_cons, where); complement_pos(sel_cons, where);
} }
static unsigned char static unsigned char
sel_pos(int n) sel_pos(int n)
{ {
return inverse_translate(vc_cons[sel_cons].d, screen_glyph(sel_cons, n)); return inverse_translate(sel_cons, screen_glyph(sel_cons, n));
} }
/* remove the current selection highlight, if any, /* remove the current selection highlight, if any,
...@@ -111,10 +113,10 @@ static inline unsigned short limit(const unsigned short v, const unsigned short ...@@ -111,10 +113,10 @@ static inline unsigned short limit(const unsigned short v, const unsigned short
/* set the current selection. Invoked by ioctl() or by kernel code. */ /* set the current selection. Invoked by ioctl() or by kernel code. */
int set_selection(const struct tiocl_selection __user *sel, struct tty_struct *tty) int set_selection(const struct tiocl_selection __user *sel, struct tty_struct *tty)
{ {
struct vc_data *vc = vc_cons[fg_console].d;
int sel_mode, new_sel_start, new_sel_end, spc; int sel_mode, new_sel_start, new_sel_end, spc;
char *bp, *obp; char *bp, *obp;
int i, ps, pe; int i, ps, pe;
unsigned int currcons = fg_console;
poke_blanked_console(); poke_blanked_console();
...@@ -128,12 +130,12 @@ int set_selection(const struct tiocl_selection __user *sel, struct tty_struct *t ...@@ -128,12 +130,12 @@ int set_selection(const struct tiocl_selection __user *sel, struct tty_struct *t
__get_user(ye, &sel->ye); __get_user(ye, &sel->ye);
__get_user(sel_mode, &sel->sel_mode); __get_user(sel_mode, &sel->sel_mode);
xs--; ys--; xe--; ye--; xs--; ys--; xe--; ye--;
xs = limit(xs, video_num_columns - 1); xs = limit(xs, vc->vc_cols - 1);
ys = limit(ys, video_num_lines - 1); ys = limit(ys, vc->vc_rows - 1);
xe = limit(xe, video_num_columns - 1); xe = limit(xe, vc->vc_cols - 1);
ye = limit(ye, video_num_lines - 1); ye = limit(ye, vc->vc_rows - 1);
ps = ys * video_size_row + (xs << 1); ps = ys * vc->vc_size_row + (xs << 1);
pe = ye * video_size_row + (xe << 1); pe = ye * vc->vc_size_row + (xe << 1);
if (sel_mode == TIOCL_SELCLEAR) { if (sel_mode == TIOCL_SELCLEAR) {
/* useful for screendump without selection highlights */ /* useful for screendump without selection highlights */
...@@ -154,9 +156,9 @@ int set_selection(const struct tiocl_selection __user *sel, struct tty_struct *t ...@@ -154,9 +156,9 @@ int set_selection(const struct tiocl_selection __user *sel, struct tty_struct *t
pe = tmp; pe = tmp;
} }
if (sel_cons != fg_console) { if (sel_cons != vc_cons[fg_console].d) {
clear_selection(); clear_selection();
sel_cons = fg_console; sel_cons = vc_cons[fg_console].d;
} }
switch (sel_mode) switch (sel_mode)
...@@ -173,7 +175,7 @@ int set_selection(const struct tiocl_selection __user *sel, struct tty_struct *t ...@@ -173,7 +175,7 @@ int set_selection(const struct tiocl_selection __user *sel, struct tty_struct *t
(!spc && !inword(sel_pos(ps)))) (!spc && !inword(sel_pos(ps))))
break; break;
new_sel_start = ps; new_sel_start = ps;
if (!(ps % video_size_row)) if (!(ps % vc->vc_size_row))
break; break;
} }
spc = isspace(sel_pos(pe)); spc = isspace(sel_pos(pe));
...@@ -183,14 +185,14 @@ int set_selection(const struct tiocl_selection __user *sel, struct tty_struct *t ...@@ -183,14 +185,14 @@ int set_selection(const struct tiocl_selection __user *sel, struct tty_struct *t
(!spc && !inword(sel_pos(pe)))) (!spc && !inword(sel_pos(pe))))
break; break;
new_sel_end = pe; new_sel_end = pe;
if (!((pe + 2) % video_size_row)) if (!((pe + 2) % vc->vc_size_row))
break; break;
} }
break; break;
case TIOCL_SELLINE: /* line-by-line selection */ case TIOCL_SELLINE: /* line-by-line selection */
new_sel_start = ps - ps % video_size_row; new_sel_start = ps - ps % vc->vc_size_row;
new_sel_end = pe + video_size_row new_sel_end = pe + vc->vc_size_row
- pe % video_size_row - 2; - pe % vc->vc_size_row - 2;
break; break;
case TIOCL_SELPOINTER: case TIOCL_SELPOINTER:
highlight_pointer(pe); highlight_pointer(pe);
...@@ -204,11 +206,11 @@ int set_selection(const struct tiocl_selection __user *sel, struct tty_struct *t ...@@ -204,11 +206,11 @@ int set_selection(const struct tiocl_selection __user *sel, struct tty_struct *t
/* select to end of line if on trailing space */ /* select to end of line if on trailing space */
if (new_sel_end > new_sel_start && if (new_sel_end > new_sel_start &&
!atedge(new_sel_end, video_size_row) && !atedge(new_sel_end, vc->vc_size_row) &&
isspace(sel_pos(new_sel_end))) { isspace(sel_pos(new_sel_end))) {
for (pe = new_sel_end + 2; ; pe += 2) for (pe = new_sel_end + 2; ; pe += 2)
if (!isspace(sel_pos(pe)) || if (!isspace(sel_pos(pe)) ||
atedge(pe, video_size_row)) atedge(pe, vc->vc_size_row))
break; break;
if (isspace(sel_pos(pe))) if (isspace(sel_pos(pe)))
new_sel_end = pe; new_sel_end = pe;
...@@ -255,7 +257,7 @@ int set_selection(const struct tiocl_selection __user *sel, struct tty_struct *t ...@@ -255,7 +257,7 @@ int set_selection(const struct tiocl_selection __user *sel, struct tty_struct *t
*bp = sel_pos(i); *bp = sel_pos(i);
if (!isspace(*bp++)) if (!isspace(*bp++))
obp = bp; obp = bp;
if (! ((i + 2) % video_size_row)) { if (! ((i + 2) % vc->vc_size_row)) {
/* strip trailing blanks from line and add newline, /* strip trailing blanks from line and add newline,
unless non-space at end of line. */ unless non-space at end of line. */
if (obp != bp) { if (obp != bp) {
......
...@@ -59,7 +59,7 @@ vcs_size(struct inode *inode) ...@@ -59,7 +59,7 @@ vcs_size(struct inode *inode)
if (!vc_cons_allocated(currcons)) if (!vc_cons_allocated(currcons))
return -ENXIO; return -ENXIO;
size = video_num_lines * video_num_columns; size = vc_cons[currcons].d->vc_rows * vc_cons[currcons].d->vc_cols;
if (minor & 128) if (minor & 128)
size = 2*size + HEADER_SIZE; size = 2*size + HEADER_SIZE;
...@@ -99,6 +99,7 @@ vcs_read(struct file *file, char __user *buf, size_t count, loff_t *ppos) ...@@ -99,6 +99,7 @@ vcs_read(struct file *file, char __user *buf, size_t count, loff_t *ppos)
{ {
struct inode *inode = file->f_dentry->d_inode; struct inode *inode = file->f_dentry->d_inode;
unsigned int currcons = iminor(inode); unsigned int currcons = iminor(inode);
struct vc_data *vc;
long pos; long pos;
long viewed, attr, read; long viewed, attr, read;
int col, maxcol; int col, maxcol;
...@@ -126,6 +127,7 @@ vcs_read(struct file *file, char __user *buf, size_t count, loff_t *ppos) ...@@ -126,6 +127,7 @@ vcs_read(struct file *file, char __user *buf, size_t count, loff_t *ppos)
ret = -ENXIO; ret = -ENXIO;
if (!vc_cons_allocated(currcons)) if (!vc_cons_allocated(currcons))
goto unlock_out; goto unlock_out;
vc = vc_cons[currcons].d;
ret = -EINVAL; ret = -EINVAL;
if (pos < 0) if (pos < 0)
...@@ -159,15 +161,15 @@ vcs_read(struct file *file, char __user *buf, size_t count, loff_t *ppos) ...@@ -159,15 +161,15 @@ vcs_read(struct file *file, char __user *buf, size_t count, loff_t *ppos)
con_buf_start = con_buf0 = con_buf; con_buf_start = con_buf0 = con_buf;
orig_count = this_round; orig_count = this_round;
maxcol = video_num_columns; maxcol = vc->vc_cols;
if (!attr) { if (!attr) {
org = screen_pos(currcons, p, viewed); org = screen_pos(vc, p, viewed);
col = p % maxcol; col = p % maxcol;
p += maxcol - col; p += maxcol - col;
while (this_round-- > 0) { while (this_round-- > 0) {
*con_buf0++ = (vcs_scr_readw(currcons, org++) & 0xff); *con_buf0++ = (vcs_scr_readw(vc, org++) & 0xff);
if (++col == maxcol) { if (++col == maxcol) {
org = screen_pos(currcons, p, viewed); org = screen_pos(vc, p, viewed);
col = 0; col = 0;
p += maxcol; p += maxcol;
} }
...@@ -176,9 +178,9 @@ vcs_read(struct file *file, char __user *buf, size_t count, loff_t *ppos) ...@@ -176,9 +178,9 @@ vcs_read(struct file *file, char __user *buf, size_t count, loff_t *ppos)
if (p < HEADER_SIZE) { if (p < HEADER_SIZE) {
size_t tmp_count; size_t tmp_count;
con_buf0[0] = (char) video_num_lines; con_buf0[0] = (char)vc->vc_rows;
con_buf0[1] = (char) video_num_columns; con_buf0[1] = (char)vc->vc_cols;
getconsxy(currcons, con_buf0 + 2); getconsxy(vc, con_buf0 + 2);
con_buf_start += p; con_buf_start += p;
this_round += p; this_round += p;
...@@ -214,7 +216,7 @@ vcs_read(struct file *file, char __user *buf, size_t count, loff_t *ppos) ...@@ -214,7 +216,7 @@ vcs_read(struct file *file, char __user *buf, size_t count, loff_t *ppos)
p /= 2; p /= 2;
col = p % maxcol; col = p % maxcol;
org = screen_pos(currcons, p, viewed); org = screen_pos(vc, p, viewed);
p += maxcol - col; p += maxcol - col;
/* Buffer has even length, so we can always copy /* Buffer has even length, so we can always copy
...@@ -224,10 +226,10 @@ vcs_read(struct file *file, char __user *buf, size_t count, loff_t *ppos) ...@@ -224,10 +226,10 @@ vcs_read(struct file *file, char __user *buf, size_t count, loff_t *ppos)
this_round = (this_round + 1) >> 1; this_round = (this_round + 1) >> 1;
while (this_round) { while (this_round) {
*tmp_buf++ = vcs_scr_readw(currcons, org++); *tmp_buf++ = vcs_scr_readw(vc, org++);
this_round --; this_round --;
if (++col == maxcol) { if (++col == maxcol) {
org = screen_pos(currcons, p, viewed); org = screen_pos(vc, p, viewed);
col = 0; col = 0;
p += maxcol; p += maxcol;
} }
...@@ -270,6 +272,7 @@ vcs_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos) ...@@ -270,6 +272,7 @@ vcs_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos)
{ {
struct inode *inode = file->f_dentry->d_inode; struct inode *inode = file->f_dentry->d_inode;
unsigned int currcons = iminor(inode); unsigned int currcons = iminor(inode);
struct vc_data *vc;
long pos; long pos;
long viewed, attr, size, written; long viewed, attr, size, written;
char *con_buf0; char *con_buf0;
...@@ -299,6 +302,7 @@ vcs_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos) ...@@ -299,6 +302,7 @@ vcs_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos)
ret = -ENXIO; ret = -ENXIO;
if (!vc_cons_allocated(currcons)) if (!vc_cons_allocated(currcons))
goto unlock_out; goto unlock_out;
vc = vc_cons[currcons].d;
size = vcs_size(inode); size = vcs_size(inode);
ret = -EINVAL; ret = -EINVAL;
...@@ -351,10 +355,10 @@ vcs_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos) ...@@ -351,10 +355,10 @@ vcs_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos)
con_buf0 = con_buf; con_buf0 = con_buf;
orig_count = this_round; orig_count = this_round;
maxcol = video_num_columns; maxcol = vc->vc_cols;
p = pos; p = pos;
if (!attr) { if (!attr) {
org0 = org = screen_pos(currcons, p, viewed); org0 = org = screen_pos(vc, p, viewed);
col = p % maxcol; col = p % maxcol;
p += maxcol - col; p += maxcol - col;
...@@ -362,11 +366,11 @@ vcs_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos) ...@@ -362,11 +366,11 @@ vcs_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos)
unsigned char c = *con_buf0++; unsigned char c = *con_buf0++;
this_round--; this_round--;
vcs_scr_writew(currcons, vcs_scr_writew(vc,
(vcs_scr_readw(currcons, org) & 0xff00) | c, org); (vcs_scr_readw(vc, org) & 0xff00) | c, org);
org++; org++;
if (++col == maxcol) { if (++col == maxcol) {
org = screen_pos(currcons, p, viewed); org = screen_pos(vc, p, viewed);
col = 0; col = 0;
p += maxcol; p += maxcol;
} }
...@@ -375,34 +379,34 @@ vcs_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos) ...@@ -375,34 +379,34 @@ vcs_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos)
if (p < HEADER_SIZE) { if (p < HEADER_SIZE) {
char header[HEADER_SIZE]; char header[HEADER_SIZE];
getconsxy(currcons, header + 2); getconsxy(vc, header + 2);
while (p < HEADER_SIZE && this_round > 0) { while (p < HEADER_SIZE && this_round > 0) {
this_round--; this_round--;
header[p++] = *con_buf0++; header[p++] = *con_buf0++;
} }
if (!viewed) if (!viewed)
putconsxy(currcons, header + 2); putconsxy(vc, header + 2);
} }
p -= HEADER_SIZE; p -= HEADER_SIZE;
col = (p/2) % maxcol; col = (p/2) % maxcol;
if (this_round > 0) { if (this_round > 0) {
org0 = org = screen_pos(currcons, p/2, viewed); org0 = org = screen_pos(vc, p/2, viewed);
if ((p & 1) && this_round > 0) { if ((p & 1) && this_round > 0) {
char c; char c;
this_round--; this_round--;
c = *con_buf0++; c = *con_buf0++;
#ifdef __BIG_ENDIAN #ifdef __BIG_ENDIAN
vcs_scr_writew(currcons, c | vcs_scr_writew(vc, c |
(vcs_scr_readw(currcons, org) & 0xff00), org); (vcs_scr_readw(vc, org) & 0xff00), org);
#else #else
vcs_scr_writew(currcons, (c << 8) | vcs_scr_writew(vc, (c << 8) |
(vcs_scr_readw(currcons, org) & 0xff), org); (vcs_scr_readw(vc, org) & 0xff), org);
#endif #endif
org++; org++;
p++; p++;
if (++col == maxcol) { if (++col == maxcol) {
org = screen_pos(currcons, p/2, viewed); org = screen_pos(vc, p/2, viewed);
col = 0; col = 0;
} }
} }
...@@ -413,11 +417,11 @@ vcs_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos) ...@@ -413,11 +417,11 @@ vcs_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos)
unsigned short w; unsigned short w;
w = get_unaligned(((const unsigned short *)con_buf0)); w = get_unaligned(((const unsigned short *)con_buf0));
vcs_scr_writew(currcons, w, org++); vcs_scr_writew(vc, w, org++);
con_buf0 += 2; con_buf0 += 2;
this_round -= 2; this_round -= 2;
if (++col == maxcol) { if (++col == maxcol) {
org = screen_pos(currcons, p, viewed); org = screen_pos(vc, p, viewed);
col = 0; col = 0;
p += maxcol; p += maxcol;
} }
...@@ -427,9 +431,9 @@ vcs_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos) ...@@ -427,9 +431,9 @@ vcs_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos)
c = *con_buf0++; c = *con_buf0++;
#ifdef __BIG_ENDIAN #ifdef __BIG_ENDIAN
vcs_scr_writew(currcons, (vcs_scr_readw(currcons, org) & 0xff) | (c << 8), org); vcs_scr_writew(vc, (vcs_scr_readw(vc, org) & 0xff) | (c << 8), org);
#else #else
vcs_scr_writew(currcons, (vcs_scr_readw(currcons, org) & 0xff00) | c, org); vcs_scr_writew(vc, (vcs_scr_readw(vc, org) & 0xff00) | c, org);
#endif #endif
} }
} }
......
This diff is collapsed.
...@@ -37,7 +37,7 @@ char vt_dont_switch; ...@@ -37,7 +37,7 @@ char vt_dont_switch;
extern struct tty_driver *console_driver; extern struct tty_driver *console_driver;
#define VT_IS_IN_USE(i) (console_driver->ttys[i] && console_driver->ttys[i]->count) #define VT_IS_IN_USE(i) (console_driver->ttys[i] && console_driver->ttys[i]->count)
#define VT_BUSY(i) (VT_IS_IN_USE(i) || i == fg_console || i == sel_cons) #define VT_BUSY(i) (VT_IS_IN_USE(i) || i == fg_console || vc_cons[i].d == sel_cons)
/* /*
* Console (vt and kd) routines, as defined by USL SVR4 manual, and by * Console (vt and kd) routines, as defined by USL SVR4 manual, and by
......
...@@ -9,6 +9,8 @@ ...@@ -9,6 +9,8 @@
* to achieve effects such as fast scrolling by changing the origin. * to achieve effects such as fast scrolling by changing the origin.
*/ */
struct vt_struct;
#define NPAR 16 #define NPAR 16
struct vc_data { struct vc_data {
...@@ -87,6 +89,7 @@ struct vc_data { ...@@ -87,6 +89,7 @@ struct vc_data {
struct vc_data **vc_display_fg; /* [!] Ptr to var holding fg console for this display */ struct vc_data **vc_display_fg; /* [!] Ptr to var holding fg console for this display */
unsigned long vc_uni_pagedir; unsigned long vc_uni_pagedir;
unsigned long *vc_uni_pagedir_loc; /* [!] Location of uni_pagedir variable for this console */ unsigned long *vc_uni_pagedir_loc; /* [!] Location of uni_pagedir variable for this console */
struct vt_struct *vc_vt;
/* additional information is in vt_kern.h */ /* additional information is in vt_kern.h */
}; };
......
...@@ -10,7 +10,7 @@ ...@@ -10,7 +10,7 @@
#include <linux/tiocl.h> #include <linux/tiocl.h>
#include <linux/vt_buffer.h> #include <linux/vt_buffer.h>
extern int sel_cons; extern struct vc_data *sel_cons;
extern void clear_selection(void); extern void clear_selection(void);
extern int set_selection(const struct tiocl_selection __user *sel, struct tty_struct *tty); extern int set_selection(const struct tiocl_selection __user *sel, struct tty_struct *tty);
...@@ -19,11 +19,6 @@ extern int sel_loadlut(char __user *p); ...@@ -19,11 +19,6 @@ extern int sel_loadlut(char __user *p);
extern int mouse_reporting(void); extern int mouse_reporting(void);
extern void mouse_report(struct tty_struct * tty, int butt, int mrx, int mry); extern void mouse_report(struct tty_struct * tty, int butt, int mrx, int mry);
#define video_num_columns (vc_cons[currcons].d->vc_cols)
#define video_num_lines (vc_cons[currcons].d->vc_rows)
#define video_size_row (vc_cons[currcons].d->vc_size_row)
#define can_do_color (vc_cons[currcons].d->vc_can_do_color)
extern int console_blanked; extern int console_blanked;
extern unsigned char color_table[]; extern unsigned char color_table[];
...@@ -31,15 +26,15 @@ extern int default_red[]; ...@@ -31,15 +26,15 @@ extern int default_red[];
extern int default_grn[]; extern int default_grn[];
extern int default_blu[]; extern int default_blu[];
extern unsigned short *screen_pos(int currcons, int w_offset, int viewed); extern unsigned short *screen_pos(struct vc_data *vc, int w_offset, int viewed);
extern u16 screen_glyph(int currcons, int offset); extern u16 screen_glyph(struct vc_data *vc, int offset);
extern void complement_pos(int currcons, int offset); extern void complement_pos(struct vc_data *vc, int offset);
extern void invert_screen(int currcons, int offset, int count, int shift); extern void invert_screen(struct vc_data *vc, int offset, int count, int shift);
extern void getconsxy(int currcons, unsigned char *p); extern void getconsxy(struct vc_data *vc, unsigned char *p);
extern void putconsxy(int currcons, unsigned char *p); extern void putconsxy(struct vc_data *vc, unsigned char *p);
extern u16 vcs_scr_readw(int currcons, const u16 *org); extern u16 vcs_scr_readw(struct vc_data *vc, const u16 *org);
extern void vcs_scr_writew(int currcons, u16 val, u16 *org); extern void vcs_scr_writew(struct vc_data *vc, u16 val, u16 *org);
#endif #endif
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment