22 #include <linux/kernel.h>
24 #include <linux/errno.h>
25 #include <linux/export.h>
26 #include <linux/tty.h>
34 #include <linux/device.h>
35 #include <linux/sched.h>
37 #include <linux/poll.h>
38 #include <linux/signal.h>
39 #include <linux/slab.h>
42 #include <asm/uaccess.h>
43 #include <asm/byteorder.h>
44 #include <asm/unaligned.h>
51 #define CON_BUF_SIZE (CONFIG_BASE_SMALL ? 256 : PAGE_SIZE)
77 if (currcons != vc->
vc_num)
106 poll->
notifier.notifier_call = vcs_notifier;
125 vcs_poll_data_free(poll);
128 spin_unlock(&file->
f_lock);
140 unsigned int currcons = iminor(inode) & 127;
161 vcs_size(
struct inode *inode)
164 int minor = iminor(inode);
169 vc = vcs_vc(inode,
NULL);
180 static loff_t vcs_lseek(
struct file *file, loff_t
offset,
int orig)
185 size = vcs_size(file->
f_path.dentry->d_inode);
196 offset += file->
f_pos;
209 vcs_read(
struct file *file,
char __user *
buf,
size_t count, loff_t *ppos)
211 struct inode *inode = file->
f_path.dentry->d_inode;
212 unsigned int currcons = iminor(inode);
217 int col, maxcol, viewed;
218 unsigned short *org =
NULL;
233 attr = (currcons & 128);
235 vc = vcs_vc(inode, &viewed);
248 char *con_buf0, *con_buf_start;
249 long this_round,
size;
257 size = vcs_size(inode);
266 if (count > size - pos)
278 con_buf_start = con_buf0 = con_buf;
279 orig_count = this_round;
285 while (this_round-- > 0) {
287 if (++col == maxcol) {
298 con_buf0[1] = (
char)vc->
vc_cols;
305 orig_count = this_round -
p;
309 if (tmp_count > this_round)
310 tmp_count = this_round;
313 this_round -= tmp_count;
328 if (this_round > 0) {
329 unsigned short *tmp_buf = (
unsigned short *)con_buf0;
342 this_round = (this_round + 1) >> 1;
347 if (++col == maxcol) {
368 read += (orig_count -
ret);
387 vcs_write(
struct file *file,
const char __user *buf,
size_t count, loff_t *ppos)
389 struct inode *inode = file->
f_path.dentry->d_inode;
390 unsigned int currcons = iminor(inode);
395 int col, maxcol, viewed;
411 attr = (currcons & 128);
413 vc = vcs_vc(inode, &viewed);
417 size = vcs_size(inode);
419 if (pos < 0 || pos > size)
421 if (count > size - pos)
425 long this_round =
count;
456 size = vcs_size(inode);
465 if (this_round > size - pos)
466 this_round = size -
pos;
473 orig_count = this_round;
481 while (this_round > 0) {
482 unsigned char c = *con_buf0++;
488 if (++col == maxcol) {
499 while (p < HEADER_SIZE && this_round > 0) {
501 header[p++] = *con_buf0++;
507 col = (p/2) % maxcol;
508 if (this_round > 0) {
510 if ((p & 1) && this_round > 0) {
524 if (++col == maxcol) {
532 while (this_round > 1) {
539 if (++col == maxcol) {
545 if (this_round > 0) {
557 written += orig_count;
581 poll_wait(file, &poll->
waitq, wait);
589 vcs_fasync(
int fd,
struct file *file,
int on)
597 poll = vcs_poll_data_get(file);
606 vcs_open(
struct inode *inode,
struct file *filp)
608 unsigned int currcons = iminor(inode) & 127;
618 static int vcs_release(
struct inode *inode,
struct file *file)
623 vcs_poll_data_free(poll);
632 .fasync = vcs_fasync,
634 .release = vcs_release,
637 static struct class *vc_class;
644 "vcsa%u", index + 1);
657 if (register_chrdev(
VCS_MAJOR,
"vcs", &vcs_fops))