|
|
1.1 root 1: /*
2: * mm.c
3: *
4: * Memory Mapped Video
5: * High level output routines.
6: *
7: * $Log: vtmm.c,v $
8: * Revision 1.2 92/07/16 16:35:31 hal
9: * Kernel #58
10: *
11: * Revision 1.4 92/04/09 10:25:38 hal
12: * Call mmgo() from mmstart() at low priority.
13: *
14: */
15: #include <sys/coherent.h>
16: #include <sys/sched.h>
17: #include <errno.h>
18: #include <sys/stat.h>
19: #include <sys/io.h>
20: #include <sys/tty.h>
21: #include <sys/timeout.h>
22:
23: #include <sys/kb.h>
24: #include <sys/vt.h>
25:
26: /* For beeper */
27: #define TIMCTL 0x43 /* Timer control port */
28: #define TIMCNT 0x42 /* Counter timer port */
29: #define PORTB 0x61 /* Port containing speaker enable */
30: #define FREQ ((int)(1193181L/440)) /* Counter for 440 Hz. tone */
31:
32: int mmtime();
33:
34: char mmbeeps; /* number of ticks remaining on bell */
35: char mmesc; /* last unserviced escape character */
36: int mmcrtsav = 1; /* crt saver enabled */
37: int mmvcnt = 900; /* seconds remaining before crt saver is activated */
38:
39: extern TTY **vttty;
40:
41: /*
42: * Start the output stream.
43: * Called from `ttwrite' and `isrint' routines.
44: */
45: TIM mmtim;
46:
47: mmstart(tp)
48: register TTY *tp;
49: {
50: int c, s;
51: IO iob;
52: static int mmbegun;
53:
54: if (mmbegun == 0) {
55: ++mmbegun;
56: timeout(&mmtim, HZ/10, mmtime, (char *)tp);
57: }
58:
59: while ((tp->t_flags&T_STOP) == 0) {
60: if ((c = ttout(tp)) < 0)
61: break;
62: iob.io_seg = IOSYS;
63: iob.io_ioc = 1;
64: iob.io.vbase = &c;
65: iob.io_flag = 0;
66: #if 0
67: mmwrite( ((VTDATA *)tp->t_ddp)->vt_dev, &iob );
68: #else
69: s = splo();
70: mmgo(&iob, tp->t_ddp, ((VTDATA *)(tp->t_ddp))->vt_ind);
71: spl(s);
72: #endif
73: }
74: }
75:
76: mmtime(xp)
77: char *xp;
78: {
79: register int s;
80: register VTDATA *vp = (VTDATA *)((TTY *)xp)->t_ddp;
81:
82: s = sphi();
83: if (mmbeeps < 0) {
84: mmbeeps = 2;
85: outb(TIMCTL, 0xB6); /* Timer 2, lsb, msb, binary */
86: outb(TIMCNT, FREQ&0xFF);
87: outb(TIMCNT, FREQ>>8);
88: outb(PORTB, inb(PORTB) | 03); /* Turn speaker on */
89: }
90: else if ((mmbeeps > 0) && (--mmbeeps == 0))
91: outb( PORTB, inb(PORTB) & ~03 );
92:
93: if (vp->vmm_esc) {
94: ismmfunc(vp->vmm_esc);
95: vp->vmm_esc = 0;
96: }
97: spl(s);
98:
99: ttstart( (TTY *) xp );
100:
101: timeout(&mmtim, HZ/10, mmtime, xp);
102: }
103:
104: /**
105: *
106: * void
107: * mmwatch() -- turn video display off after 15 minutes inactivity.
108: */
109: void
110: mmwatch()
111: {
112: if ( (mmcrtsav > 0) && (mmvcnt > 0) && (--mmvcnt == 0) ) {
113: mm_voff(vtdata[vtactive]);
114: }
115: }
116:
117: mmwrite( dev, iop )
118: dev_t dev;
119: register IO *iop;
120: {
121: int ioc;
122: register TTY *tp = vttty[vtindex(dev)];
123:
124: if (!tp) {
125: printf( "mmwrite: bad dev %x", dev );
126: }
127: /*
128: * Kernel writes.
129: */
130: if (iop->io_seg == IOSYS) {
131: while (mmgo(iop, tp->t_ddp, vtindex(dev)))
132: ;
133: goto mmwdone;
134: }
135:
136: #if 0
137: ioc = iop->io_ioc;
138: /*
139: * Blocking user writes.
140: */
141: if ( (iop->io_flag & IONDLY) == 0 ) {
142: do {
143: while (tp->t_flags & T_STOP) {
144: register s = sphi();
145:
146: tp->t_flags |= T_HILIM;
147: sleep((char*) &tp->t_oq,
148: CVTTOUT, IVTTOUT, SVTTOUT);
149: spl( s );
150: }
151: /*
152: * Signal received.
153: */
154: if ( SELF->p_ssig && nondsig() ) {
155: kbunscroll(); /* update kbd LEDS */
156: /*
157: * No data transferred yet.
158: */
159: if ( ioc == iop->io_ioc )
160: u.u_error = EINTR;
161: /*
162: * Transfer remaining data
163: * without pausing after scrolling.
164: */
165: else while ( mmgo(iop, tp->t_ddp, vtindex(dev)))
166: ;
167: goto mmwdone;
168: }
169: mmgo(iop, tp->t_ddp, vtindex(dev));
170: } while ( iop->io_ioc );
171: goto mmwdone;
172: }
173:
174: /*
175: * Non-blocking user writes with output stopped.
176: */
177: if ( tp->t_flags & T_STOP ) {
178: u.u_error = EAGAIN;
179: goto mmwdone;
180: }
181:
182: /*
183: * Non-blocking user writes do not pause after scrolling.
184: */
185: {
186: while ( mmgo(iop, tp->t_ddp, vtindex(dev)) )
187: ;
188: }
189: #else
190: ttwrite(tp, iop);
191: #endif
192: mmwdone:
193: return;
194: }
195:
196: /******************************************************************************
197: *
198: * The following routines are called by deferred isr's, i.e., no sleep() calls
199: * allowed
200: *
201: *******************************************************************************/
202:
203: /*
204: * update the screen to match vtactive
205: */
206: updscreen(index)
207: int index;
208: {
209: register int pos, s;
210: VTDATA *vp;
211:
212: vp = vtdata[index];
213: pos = vp->vmm_voff;
214: PRINTV( "update screen@%x {%d @%x|",
215: vp->vmm_port, index, pos );
216:
217: s = sphi();
218: /* update base of video memory */
219: outb(vp->vmm_port, 0xC);
220: outb(vp->vmm_port+1, pos >> (8 + 1) );
221: outb(vp->vmm_port, 0xD);
222: outb(vp->vmm_port+1, pos >> (0 + 1) );
223:
224: /* update the cursor */
225: pos += vp->vmm_pos;
226:
227: pos |= vp->vmm_invis; /* Mask cursor, if set */
228: outb(vp->vmm_port, 0xE);
229: outb(vp->vmm_port+1, pos >> (8 + 1) );
230: outb(vp->vmm_port, 0xF);
231: outb(vp->vmm_port+1, pos >> (0 + 1) );
232:
233: spl(s);
234: PRINTV( "%x}\n", pos );
235: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.