|
|
1.1 ! root 1: /* ! 2: * Special Getline for tabbld. Keeps comments in char *comment. ! 3: * ! 4: * char * getline(ifp, lineno) FILE *ifp; int *lineno; ! 5: * ! 6: * Function to get lines from an input file. ! 7: * Returns the address of the line, or NULL for eof. ! 8: * ! 9: * lineno should usually be started at 1. lineno will ! 10: * be incremented by the number of lines in the previous call. ! 11: * Thus lineno will be the number of the line just gotten. ! 12: * ! 13: * # to end of line is ignored. ! 14: * \ whitespace through end of line is ignored. ! 15: * \n newline ! 16: * \p # ! 17: * \b backspace ! 18: * \r carrage return ! 19: * \f form feed ! 20: * \t tab ! 21: * \\ backslash ! 22: * \ddd octal number ! 23: * all other \ sequences are errors. ! 24: */ ! 25: #include <misc.h> ! 26: ! 27: extern char *realloc(); ! 28: ! 29: static char *line = NULL; ! 30: char *comment = NULL; ! 31: static int oldline = 0; ! 32: static int i = 0, size = 0; /* stuff for line */ ! 33: static int j = 0, csize = 0; /* stuff for comment */ ! 34: ! 35: /* ! 36: * Add char to line. ! 37: */ ! 38: static void ! 39: addchr(c) ! 40: { ! 41: while (i >= size) ! 42: if (NULL == (line = realloc(line, size += 80))) ! 43: fatal("Out of space"); ! 44: /* NODOC */ ! 45: line[i++] = c; ! 46: } ! 47: ! 48: /* ! 49: * Add char to comment. ! 50: */ ! 51: static void ! 52: addcom(c) ! 53: { ! 54: while (j >= csize) ! 55: if (NULL == (comment = realloc(comment, csize += 80))) ! 56: fatal("Out of space"); /* NODOC */ ! 57: comment[j++] = c; ! 58: } ! 59: ! 60: char * ! 61: getline(ifp, lineno) ! 62: FILE *ifp; ! 63: int *lineno; ! 64: { ! 65: int c, octacc, octcnt; ! 66: enum state { normal, incont, incomm, incommb, bsl, octdig } state; ! 67: ! 68: *lineno += oldline; ! 69: for (state = normal, oldline = j = i = 0;;) { ! 70: if (EOF == (c = fgetc(ifp))) { ! 71: if (i) ! 72: fprintf(stderr, ! 73: "line %d truncated at end\n", ! 74: *lineno + oldline); ! 75: return (NULL); ! 76: } ! 77: ! 78: switch (state) { ! 79: case normal: ! 80: switch (c) { ! 81: case '\\': ! 82: state = bsl; ! 83: continue; ! 84: ! 85: case '#': ! 86: state = incomm; ! 87: continue; ! 88: ! 89: case '\n': ! 90: oldline++; ! 91: addcom(0); ! 92: addchr(0); ! 93: return (line); ! 94: } ! 95: ! 96: addchr(c); ! 97: continue; ! 98: ! 99: case incont: ! 100: if ('\n' == c) { ! 101: oldline++; ! 102: state = normal; ! 103: } ! 104: continue; ! 105: ! 106: case incomm: ! 107: switch (c) { ! 108: case ' ': ! 109: case '\t': ! 110: continue; ! 111: case '\n': ! 112: state = normal; ! 113: oldline++; ! 114: addchr(0); ! 115: addcom(0); ! 116: return (line); ! 117: } ! 118: state = incommb; ! 119: addcom(c); ! 120: continue; ! 121: ! 122: case incommb: ! 123: if ('\n' == c) { ! 124: state = normal; ! 125: oldline++; ! 126: addchr(0); ! 127: addcom(0); ! 128: return (line); ! 129: } ! 130: addcom(c); ! 131: continue; ! 132: ! 133: case bsl: ! 134: switch (c) { ! 135: case 'b': ! 136: c = '\b'; ! 137: ! 138: case '\\': ! 139: break; ! 140: ! 141: case 'p': ! 142: c = '#'; ! 143: break; ! 144: ! 145: case 'f': ! 146: c = '\f'; ! 147: break; ! 148: ! 149: case 'a': ! 150: c = '\a'; ! 151: break; ! 152: ! 153: case 'r': ! 154: c = '\r'; ! 155: break; ! 156: ! 157: case 't': ! 158: c = '\t'; ! 159: break; ! 160: ! 161: case 'n': ! 162: c = '\n'; ! 163: break; ! 164: ! 165: case ' ': ! 166: case '\t': ! 167: state = incont; ! 168: continue; ! 169: ! 170: case '\n': ! 171: oldline++; ! 172: state = normal; ! 173: continue; ! 174: ! 175: default: ! 176: if (('0' <= c) && ('7' >= c)) { ! 177: state = octdig; ! 178: octcnt = 1; ! 179: octacc = c - '0'; ! 180: continue; ! 181: } ! 182: fprintf(stderr, ! 183: "%d: '%c' 0x%2x after \\\n", ! 184: *lineno + oldline, c, c); ! 185: } ! 186: state = normal; ! 187: addchr(c); ! 188: continue; ! 189: ! 190: case octdig: ! 191: if (('0' <= c) && ('7' >= c)) { ! 192: octacc *= 8; ! 193: octacc += c - '0'; ! 194: if (3 == ++octcnt) { ! 195: state = normal; ! 196: addchr(octacc); ! 197: } ! 198: } ! 199: else { ! 200: ungetc(c, ifp); ! 201: state = normal; ! 202: addchr(octacc); ! 203: } ! 204: continue; ! 205: } ! 206: } ! 207: ! 208: } ! 209: ! 210: #ifdef TEST ! 211: main() ! 212: { ! 213: int line = 1; ! 214: char *got; ! 215: ! 216: for (;;) { ! 217: if (NULL == (got = getline(stdin, &line))) ! 218: exit(0); ! 219: ! 220: if (*comment) ! 221: printf("%d: %s #%s\n", line, got, comment); ! 222: else ! 223: printf("%d: %s\n", line, got); ! 224: } ! 225: } ! 226: #endif
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.