|
|
1.1 ! root 1: #include <jerq.h> ! 2: #include "queue.h" ! 3: #include <kbd.h> ! 4: #include <setup.h> ! 5: ! 6: #define ESC '\033' ! 7: #define ESCB 0200 ! 8: #define DEL '\177' ! 9: #define K_KEY 0 ! 10: #define K_CHAR 1 ! 11: ! 12: /* ! 13: * Note that the keypad keys send what they say. ! 14: * the arrows send 'escape [' followed by A, B, C, D, H, except for HOME DOWN, ! 15: * which sends (ugh) esc [ 70;0H. Clear sends esc[0J, ! 16: * Break, disconnect, and the pf keys send codes 0x80 through 0x89 respectively. ! 17: * If you want to tell the keypad numbers from the real ones, work in raw. ! 18: * The keytab table has been drastically extended for the TTYKBD and ! 19: * a binary search is now used. Why could'nt they generate sane codes!! ! 20: * WARNING, the keytab entries must be sorted into ascending order! ! 21: * For any ordinary "key", char c is sent. The arrow keys or 0x80 with ! 22: * the ascii letter needed to send, except for HOME DOWN. HOME DOWN ! 23: * and Clear are done by 0x8a and 0x8b, respectively, and break, ! 24: * disconnect and pfkeys are entered as shown above. ! 25: */ ! 26: ! 27: unsigned char keytab[][2] = { ! 28: 0x8f, 0x81, /* shifted key 42, discon */ ! 29: 0x90, ESCB | 'B', /* shifted key 109, down arrow */ ! 30: 0x91, ESCB | 'H', /* shifted key 97, left-up arrow */ ! 31: 0x92, ESCB | 'A', /* shifted key 98, up arrow */ ! 32: 0x93, ESCB | 0xa, /* shifted key 99, home down arrow */ ! 33: 0x94, '4', /* shifted key 79, 4 */ ! 34: 0x95, '5', /* shifted key 80, 5 */ ! 35: 0x96, '6', /* shifted key 81, 6 */ ! 36: 0x97, '7', /* shifted key 60, 7 */ ! 37: 0x98, '8', /* shifted key 61, 8 */ ! 38: 0x99, '9', /* shifted key 62, 9 */ ! 39: 0x9a, ESCB | 'D', /* shifted key 108, left arrow */ ! 40: 0x9b, ESCB | 'C', /* shifted key 110, right arrow */ ! 41: 0xaf, 0x80, /* unshifted key 42, break */ ! 42: 0xb0, '\0', /* control key 35, ignored */ ! 43: 0xb1, '\0', /* control key 26, ignored */ ! 44: 0xb3, '\0', /* control key 28, ignored */ ! 45: 0xb4, '\0', /* control key 29, ignored */ ! 46: 0xb5, '\0', /* control key 30, ignored */ ! 47: 0xb6, '\012', /* unshifted key 96, line-feed */ ! 48: 0xb7, '\0', /* control key 32, ignored */ ! 49: 0xb8, '\0', /* control key 33, ignored */ ! 50: 0xb9, '\0', /* control key 34, ignored */ ! 51: 0xba, '\0', /* control key 27, ignored */ ! 52: 0xbb, '\0', /* control key 75, ignored */ ! 53: 0xbc, '\0', /* control key 31, ignored */ ! 54: 0xbd, '\0', /* control key 37, ignored */ ! 55: 0xbe, '\0', /* control key 59, ignored */ ! 56: 0xbf, '\0', /* control key 36, ignored */ ! 57: 0xc0, ESCB | 'H', /* unshifted key 97, left-up arrow */ ! 58: 0xc1, ESCB | 'A', /* unshifted key 98, up arrow */ ! 59: 0xc2, ESCB | 'B', /* unshifted key 109, down arrow */ ! 60: 0xc3, ESCB | 'C', /* unshifted key 110, right arrow */ ! 61: 0xc4, ESCB | 'D', /* unshifted key 108, left arrow */ ! 62: 0xc6, ESCB | 0xa, /* unshifted key 99, home down arrow */ ! 63: 0xc7, '\r', /* shifted key 77, return */ ! 64: 0xc8, ESCB | 2, /* shifted key 3, f1 */ ! 65: 0xc9, ESCB | 3, /* shifted key 4, f2 */ ! 66: 0xca, ESCB | 4, /* shifted key 5, f3 */ ! 67: 0xcb, ESCB | 5, /* shifted key 8, f4 */ ! 68: 0xcc, ESCB | 6, /* shifted key 9, f5 */ ! 69: 0xcd, ESCB | 7, /* shifted key 12, f6 */ ! 70: 0xce, ESCB | 8, /* shifted key 13, f7 */ ! 71: 0xcf, ESCB | 9, /* shifted key 14, f8 */ ! 72: 0xd0, '\t', /* unshifted key 45, tab */ ! 73: 0xd1, '\b', /* shifted key 38, bs */ ! 74: 0xd2, '7', /* unshifted key 60, 7 */ ! 75: 0xd3, '4', /* unshifted key 79, 4 */ ! 76: 0xd4, '8', /* unshifted key 61, 8 */ ! 77: 0xd5, '5', /* unshifted key 80, 5 */ ! 78: 0xd6, '9', /* unshifted key 62, 9 */ ! 79: 0xd7, '6', /* unshifted key 81, 6 */ ! 80: 0xde, DEL, /* shifted key 39, del */ ! 81: 0xe2, '\0', /* control key 76, */ ! 82: 0xe3, ESC, /* unshifted key 25, esc */ ! 83: 0xe5, ESCB | 0xb, /* unshifted key 40, clr */ ! 84: 0xe7, '\r', /* unshifted key 77, return */ ! 85: 0xe8, ESCB | 2, /* unshifted key 3, f1 */ ! 86: 0xe9, ESCB | 3, /* unshifted key 4, f2 */ ! 87: 0xea, ESCB | 4, /* unshifted key 5, f3 */ ! 88: 0xeb, ESCB | 5, /* unshifted key 8, f4 */ ! 89: 0xec, ESCB | 6, /* unshifted key 9, f5 */ ! 90: 0xed, ESCB | 7, /* unshifted key 12, f6 */ ! 91: 0xee, ESCB | 8, /* unshifted key 13, f7 */ ! 92: 0xef, ESCB | 9, /* unshifted key 14, f8 */ ! 93: 0xf0, '\t', /* shifted key 45, tab */ ! 94: 0xf1, '\b', /* unshifted key 38, bs */ ! 95: 0xf2, '\0', /* shifted key 107, num-lock */ ! 96: 0xf3, ESC, /* shifted key 25, esc */ ! 97: 0xf5, ESCB | 0xc, /* shifted key 40, local clear functin */ ! 98: 0xf6, '\n', /* shifted key 96, line-feed */ ! 99: 0xfe, DEL, /* unshifted key 39, del */ ! 100: }; ! 101: ! 102: ! 103: int kbdrepeat, rptcount, kbdstatus, dispstatus; ! 104: ! 105: /* lookup table for translating when keyboard uses numeric lock */ ! 106: unsigned char numlocktab[7] = {'1','2','0','.','-',0xc5,'3'}; ! 107: ! 108: kbdchar() ! 109: { ! 110: return qgetc(&KBDQUEUE); ! 111: } ! 112: ! 113: ! 114: kbdinit() ! 115: { ! 116: /* init the keyboard */ ! 117: DUART->b_cmnd = RESET_RECV | DIS_TX | DIS_RX; ! 118: DUART->b_cmnd = RESET_TRANS; ! 119: DUART->b_cmnd = RESET_ERR; ! 120: DUART->b_cmnd = RESET_MR; ! 121: DUART->mr1_2b = CHAR_ERR | PAR_ENB | EVN_PAR | CBITS8; ! 122: DUART->mr1_2b = NRML_MOD | ONEP000SB; ! 123: DUART->b_sr_csr = BD4800BPS; ! 124: DUART->b_cmnd = RESET_MR | ENB_TX | ENB_RX; ! 125: DUART->scc_ropbc = 0x08; /* set output pins for kbd tx port*/ ! 126: /* turn chirps on/off depending on BRAM */ ! 127: ! 128: if (VALKEYTONE) ! 129: kbdstatus = 0; /* no chirp */ ! 130: else ! 131: kbdstatus = TTY_CHIRP; /* chirp, chirp */ ! 132: DUART->b_data = kbdstatus | 0x02; /* request status */ ! 133: } ! 134: ! 135: auto2() ! 136: { ! 137: register i; ! 138: register start, end; ! 139: Point setupcur; ! 140: char s; ! 141: char c; ! 142: extern int blocked, ublocked; ! 143: ! 144: /* don't actually set the repeat bit until the character after the control code */ ! 145: ! 146: s = DUART->b_sr_csr; ! 147: c = DUART->b_data; ! 148: ! 149: if (s & (FRM_ERR | OVR_RUN)) ! 150: return; /* framing error or overrun error */ ! 151: ! 152: if (s & PAR_ERR) { ! 153: /* parity error indicates this is a control word */ ! 154: /* see what state caps lock is in */ ! 155: checkbram(); ! 156: VALCAPS = (c & 0x4) ? 0 : 1; /* set the caps lock flag */ ! 157: caps_msg(); ! 158: setbram(); /* must adjust checksum */ ! 159: if (c & 0x10) { ! 160: /* turn repeat off */ ! 161: kbdrepeat = 0; ! 162: rptcount = 0; ! 163: } ! 164: else { /* turn repeat on, the next character is to be repeated */ ! 165: kbdrepeat = RPTON; ! 166: } ! 167: return; ! 168: } ! 169: ! 170: rptcount = 0; /* new charcter so restart repeat timer */ ! 171: if (c & 0x80) { ! 172: switch (c & 0xff) { ! 173: case 0xb2: /* numeric lock toggle */ ! 174: case 0xf2: ! 175: if(kbdrepeat & RPTON) { ! 176: kbdrepeat = 0; /* don't want to repeat */ ! 177: return; ! 178: } ! 179: checkbram(); ! 180: VALNUM = 1 - VALNUM; ! 181: setbram(); ! 182: num_msg(); ! 183: return; ! 184: case 0x8e: /* un/shited key 41, selftest */ ! 185: test32(1); ! 186: asm(" JMP reboot"); ! 187: case 0xae: /* setup */ ! 188: if(kbdrepeat & RPTON) { ! 189: kbdrepeat = 0; /* don't want to repeat */ ! 190: return; ! 191: } ! 192: if(!ublocked && !blocked && !VALDWNLDFLAG) ! 193: sendchar(0x13); /* ^S */ ! 194: setupdisplay(); ! 195: if(!ublocked && !blocked && !VALDWNLDFLAG) ! 196: sendchar(0x11); /* ^Q */ ! 197: return; ! 198: } ! 199: if ((VALNUM) && (c >= 0xc0) && (c <= 0xc6)) { ! 200: /* what fun: software lookup of numeric */ ! 201: /* locked values... why burden the hardware */ ! 202: c = numlocktab[c - 0xc0]; ! 203: qputc(&KBDQUEUE, (int)c); ! 204: if((kbdrepeat & RPTMASK) == RPTON) { ! 205: kbdrepeat = RPTHAVECHR | RPTON; ! 206: kbdrepeat += (c & 0xff); ! 207: } ! 208: return; ! 209: } ! 210: ! 211: i = keytabsearch(c); ! 212: /* ! 213: * here either keytab[i][K_KEY] == c, or c is not in the table ! 214: * If c is not in the table, there is an error somewhere, so ring the bell ! 215: */ ! 216: if (c == keytab[i][K_KEY]) { ! 217: if(((c = (keytab[i][K_CHAR]) & 0xff) >= 0x80) && (c <= 0x89)) /* pfkey, break, disconnect, clear */ ! 218: { ! 219: if(kbdrepeat & RPTON) { ! 220: kbdrepeat = 0; /* don't want to repeat */ ! 221: return; ! 222: } ! 223: qputc( &KBDQUEUE, c ); ! 224: return; ! 225: } ! 226: kchkchar(c); ! 227: if ((kbdrepeat & RPTMASK) == RPTON) { ! 228: /* this is it! */ ! 229: kbdrepeat = RPTHAVECHR | RPTON | RPTLOOKUP; ! 230: kbdrepeat += i; ! 231: } ! 232: } ! 233: else { ! 234: ringbell(); ! 235: } ! 236: } ! 237: else { ! 238: qputc(&KBDQUEUE, (int)c); ! 239: if((kbdrepeat & RPTMASK) == RPTON) { ! 240: kbdrepeat = RPTHAVECHR | RPTON; ! 241: kbdrepeat += (c & 0xff); ! 242: } ! 243: } ! 244: } ! 245: ! 246: ! 247: ! 248: kchkchar(c) ! 249: register char c; ! 250: { ! 251: switch (c & 0xff) { ! 252: case 0x8a: /* HOME DOWN */ ! 253: qputstr( &KBDQUEUE, "\033[70;1H"); ! 254: break; ! 255: case 0x8b: /* CLEAR */ ! 256: if(kbdrepeat & RPTON) { /* turn off repeat */ ! 257: kbdrepeat = 0; ! 258: return; ! 259: } ! 260: qputstr( &KBDQUEUE, "\033[2J"); ! 261: break; ! 262: case 0x8c: /* local clear function */ ! 263: if(kbdrepeat & RPTON) { ! 264: kbdrepeat = 0; ! 265: return; ! 266: } ! 267: else ! 268: qputc(&KBDQUEUE, c); ! 269: break; ! 270: case 0x80 | 'A': ! 271: case 0x80 | 'B': ! 272: case 0x80 | 'C': ! 273: case 0x80 | 'D': ! 274: case 0x80 | 'H': ! 275: qputstr( &KBDQUEUE, "\033["); ! 276: qputc( &KBDQUEUE, c & 0x7f); ! 277: break; ! 278: default: ! 279: if (c != '\0') ! 280: qputc(&KBDQUEUE, (int)c); ! 281: } ! 282: } ! 283: ! 284: ! 285: kbdrpt() ! 286: { ! 287: char c; ! 288: ! 289: if (kbdrepeat & RPTLOOKUP) { ! 290: if ((c = keytab[kbdrepeat & 0xff][K_CHAR]) & 0x80) { ! 291: kchkchar(c); ! 292: } ! 293: else if (c != '\0') { ! 294: qputc(&KBDQUEUE, (int)c); ! 295: } ! 296: } ! 297: else { ! 298: qputc(&KBDQUEUE, kbdrepeat & 0xff); ! 299: } ! 300: } ! 301: ! 302: ! 303: ! 304: kgetc() ! 305: { ! 306: register int c; ! 307: register char s; ! 308: register start, end, i; ! 309: ! 310: if(KBDQUEUE.c_cc > 0) ! 311: return(qgetc(&KBDQUEUE)); ! 312: ! 313: while ((s = (DUART->b_sr_csr & (RCV_RDY | FRM_ERR | PAR_ERR | OVR_RUN | RCVD_BRK))) == 0) ! 314: aciapaws(); /* so we don't overload stupid part */ ! 315: ! 316: if (!(s & RCV_RDY)) ! 317: return(-1); ! 318: c = DUART->b_data; ! 319: if ((s & (FRM_ERR | PAR_ERR | OVR_RUN | RCVD_BRK)) == 0) /* just a char */ ! 320: { ! 321: if(kbdrepeat & RPTON) { ! 322: kbdrepeat = 0; /* turn off repeat */ ! 323: return(-1); ! 324: } ! 325: if (c & 0x80) { ! 326: switch (c & 0xff) { ! 327: case 0x8e: /* un/shited key 41, selftest */ ! 328: test32(1); ! 329: case 0x8f: /* shift break (disconnect) reboot the terminal */ ! 330: sendchar(0x11); /* cntl-Q */ ! 331: asm(" JMP reboot"); ! 332: case 0xae: /* setup */ ! 333: case 0xc3: /* right-arrow */ ! 334: case 0xc4: /* left-arrow */ ! 335: return(c); ! 336: case 0xb2: ! 337: case 0xf2: /* num lock key */ ! 338: VALNUM= 1 - VALNUM; ! 339: setbram(); ! 340: num_setup(); ! 341: return(-1); ! 342: } ! 343: i = keytabsearch(c); ! 344: /* ! 345: * here either keytab[i][K_KEY] == c, or c is not in the table ! 346: * If c is not in the table, there is an error somewhere, so ring the bell ! 347: */ ! 348: if (c == keytab[i][K_KEY]) { ! 349: if (((c = keytab[i][K_CHAR]) & 0xff) <= 0x89 ) /* pfkey, break, disconnect */ ! 350: return(c); ! 351: kchkchar(c); ! 352: return(-1); ! 353: } ! 354: } ! 355: else ! 356: return(c); ! 357: } ! 358: else if ((s & PAR_ERR) && (s & RCV_RDY)) ! 359: { ! 360: VALCAPS = (c & 0x4) ? 0 : 1; /* set the caps lock flag */ ! 361: cap_setup(); ! 362: setbram(); /* fix checksum */ ! 363: if(c & 0x10) { ! 364: /* not repeating anything */ ! 365: kbdrepeat = 0; ! 366: rptcount = 0; ! 367: } ! 368: else { ! 369: /* ! 370: * the keyboard will send us a character to repeat ! 371: * since we dont repeat in setup, throw the next ! 372: * character away. ! 373: */ ! 374: kbdrepeat = RPTON; ! 375: } ! 376: } ! 377: return(-1); ! 378: } ! 379: ! 380: keytabsearch(c) /* search keytab[] for char c */ ! 381: unsigned char c; ! 382: { ! 383: register int start, end, i; ! 384: /* ! 385: * Assume start, end and i are indexes into keytab, ! 386: * an array of two element structures. The elements are: ! 387: * keytab[][2], the two elements are: ! 388: * char key; ! 389: * char c; /* the char to send, 0 - not sent ! 390: * } ! 391: */ ! 392: ! 393: start = 0; ! 394: end = sizeof(keytab) / sizeof(keytab[0]); ! 395: for (i = (start + end) / 2; ! 396: (keytab[i][K_KEY] != c) && (start <= end); ! 397: i = (start + end) / 2) ! 398: if (c > keytab[i][K_KEY]) ! 399: start = i + 1; ! 400: else ! 401: end = i - 1; ! 402: ! 403: return (i); ! 404: /* ! 405: * here either keytab[i][K_KEY] == c, or c is not in the table ! 406: * If c is not in the table, there is an error somewhere, so ring the bell ! 407: * (bell gets rung by caller) ! 408: */ ! 409: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.