1: #include <X/mit-copyright.h> 2: 3: /* Copyright 1985 by the Massachusetts Institute of Technology */ 4: /* 5: * Parse and unparse ANSI sequences. 6: */ 7: #include <stdio.h> 8: #include <X/Xlib.h> 9: #include "ptyx.h" 10: 11: parseseq(c, ap, tek) 12: register int c; 13: register ANSI *ap; 14: { 15: /* 16: * Start up sequence if this is a sequence introducer. 17: */ 18: if (c==ESC || c==DCS || c==CSI || c==OSC || c==PM || c==APC) { 19: ap->a_type = c; 20: ap->a_pintro = 0; 21: ap->a_final = 0; 22: ap->a_inters = 0; 23: ap->a_nparam = 0; 24: ap->a_nastyf = 0; 25: return (-1); 26: } 27: /* 28: * Just pass the character through if not in a sequence. 29: */ 30: if (ap->a_type == 0) 31: return (c); 32: /* 33: * Abort on C1 control, cancel or random communication error. 34: */ 35: if ((c>=0x80 && c<=0x9F)) { 36: ap->a_type = 0; 37: ap->a_pintro = 0; 38: ap->a_final = 0; 39: return (c); 40: } 41: /* 42: * C0 control characters are passed through in the middle, 43: * except for a couple of special ones in Tek mode. 44: */ 45: if (c<0x20 || c==DEL || c==RDEL) { 46: if (tek 47: && ap->a_pintro==0 48: && ap->a_final==0 49: && ap->a_inters==0 50: && ap->a_nparam==0 51: && ap->a_nastyf==0) { 52: if (ap->a_type==ESC && (c==FF || c==SUB || c==INQ)) 53: goto finalchar; 54: if (ap->a_type==CSI && c==US) 55: goto finalchar; 56: } 57: if (c==CAN || c==SUB) { 58: ap->a_type = 0; 59: ap->a_pintro = 0; 60: ap->a_final = 0; 61: } 62: return (c); 63: } 64: c &= 0x7F; 65: /* 66: * Intermediate characters. 67: */ 68: if (c>=0x20 && c<=0x2F) { 69: ap->a_inters <<= 8; 70: ap->a_inters |= c; 71: return (-1); 72: } 73: /* 74: * Parameter character in DCS, CSI, et al. 75: */ 76: if (ap->a_type!=ESC && c>=0x30 && c<=0x3F) { 77: if (ap->a_inters != 0) 78: ap->a_nastyf = 1; 79: /* 80: * Only "?" and "<" are legal at Digital. 81: */ 82: if (c >= 0x3C) { 83: if (ap->a_pintro != 0 || ap->a_nparam != 0) 84: ap->a_nastyf = 1; 85: ap->a_pintro = c; 86: return (-1); 87: } 88: /* 89: * set the default flag and init param value to 0 90: * if we haven't seen any param's yet. 91: */ 92: if (ap->a_nparam == 0) { 93: ap->a_dflt[ap->a_nparam] = 1; 94: ap->a_param[ap->a_nparam++] = 0; 95: } 96: /* 97: * ";" or ":", only the ";" is legal at Digital. 98: */ 99: if (c >= 0x3A) { 100: if (c != 0x3B || ap->a_nparam >= NPARAM) 101: ap->a_nastyf = 1; 102: else { 103: ap->a_dflt[ap->a_nparam] = 1; 104: ap->a_param[ap->a_nparam++] = 0; 105: } 106: return (-1); 107: } 108: /* 109: * Part of a numeric parameter. 110: * Clear the default flag for this param. 111: */ 112: ap->a_dflt[ap->a_nparam-1] = 0; 113: ap->a_param[ap->a_nparam-1] *= 10; 114: ap->a_param[ap->a_nparam-1] += c - 0x30; 115: return (-1); 116: } 117: /* 118: * C1 control in its 7 bit ESC Fe representation. 119: */ 120: if (ap->a_type==ESC && ap->a_inters==0 && c>=0x40 && c<=0x5F) { 121: c += 0x40; 122: /* 123: * May need to start up a new sequence. 124: */ 125: if (c!=DCS && c!=CSI && c!=OSC && c!=PM && c!=APC) { 126: ap->a_type = 0; 127: ap->a_pintro = 0; 128: ap->a_final = 0; 129: return (c); 130: } 131: ap->a_type = c; 132: ap->a_pintro = 0; 133: ap->a_final = 0; 134: ap->a_nastyf = 0; 135: return (-1); 136: } 137: /* 138: * Final character in sequence. 139: */ 140: finalchar: 141: ap->a_final = c; 142: return (ap->a_type); 143: } 144: 145: unparseseq(ap, tx8flag, fd) 146: register ANSI *ap; 147: { 148: register int c; 149: register int i; 150: register int inters; 151: 152: c = ap->a_type; 153: if (c>=0x80 && c<=0x9F && tx8flag==0) { 154: unparseputc(ESC, fd); 155: c -= 0x40; 156: } 157: unparseputc(c, fd); 158: c = ap->a_type; 159: if (c==ESC || c==DCS || c==CSI || c==OSC || c==PM || c==APC) { 160: if (ap->a_pintro != 0) 161: unparseputc(ap->a_pintro, fd); 162: for (i=0; i<ap->a_nparam; ++i) { 163: if (i != 0) 164: unparseputc(';', fd); 165: if (ap->a_param[i] != 0) 166: unparseputn(ap->a_param[i], fd); 167: } 168: inters = ap->a_inters; 169: for (i=3; i>=0; --i) 170: c = (inters >> (8*i)) & 0xff; 171: if (c != 0) 172: unparseputc(c, fd); 173: unparseputc(ap->a_final, fd); 174: } 175: } 176: 177: unparseputn(n, fd) 178: unsigned int n; 179: { 180: unsigned int q; 181: 182: q = n/10; 183: if (q != 0) 184: unparseputn(q, fd); 185: unparseputc((n%10) + '0', fd); 186: } 187: 188: unparseputc(c, fd) 189: { 190: char buf[1]; 191: 192: buf[0] = c; 193: if (write(fd, buf, 1) != 1) 194: Panic("unparseputc: error writing character\n", 0); 195: }