00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024 #include "defs.h"
00025 #include "names.h"
00026 #include "output.h"
00027 #ifndef KR_headers
00028 #include "stdarg.h"
00029 #endif
00030
00031 #define TOO_LONG_INDENT (2 * tab_size)
00032 #define MAX_INDENT 44
00033 #define MIN_INDENT 22
00034 static int last_was_newline = 0;
00035 int sharp_line = 0;
00036 int indent = 0;
00037 int in_comment = 0;
00038 int in_define = 0;
00039 extern int gflag1;
00040 extern char filename[];
00041
00042 static void ind_printf Argdcl((int, FILE*, const char*, va_list));
00043
00044 static void
00045 #ifdef KR_headers
00046 write_indent(fp, use_indent, extra_indent, start, end)
00047 FILE *fp;
00048 int use_indent;
00049 int extra_indent;
00050 char *start;
00051 char *end;
00052 #else
00053 write_indent(FILE *fp, int use_indent, int extra_indent, char *start, char *end)
00054 #endif
00055 {
00056 int ind, tab;
00057
00058 if (sharp_line) {
00059 fprintf(fp, "#line %ld \"%s\"\n", lineno, filename);
00060 sharp_line = 0;
00061 }
00062 if (in_define == 1) {
00063 in_define = 2;
00064 use_indent = 0;
00065 }
00066 if (last_was_newline && use_indent) {
00067 if (*start == '\n') do {
00068 putc('\n', fp);
00069 if (++start > end)
00070 return;
00071 }
00072 while(*start == '\n');
00073
00074 ind = indent <= MAX_INDENT
00075 ? indent
00076 : MIN_INDENT + indent % (MAX_INDENT - MIN_INDENT);
00077
00078 tab = ind + extra_indent;
00079
00080 while (tab > 7) {
00081 putc ('\t', fp);
00082 tab -= 8;
00083 }
00084
00085 while (tab-- > 0)
00086 putc (' ', fp);
00087 }
00088
00089 while (start <= end)
00090 putc (*start++, fp);
00091 }
00092
00093 #ifdef KR_headers
00094
00095 void
00096 margin_printf (fp, a, b, c, d, e, f, g)
00097 FILE *fp;
00098 char *a;
00099 long b, c, d, e, f, g;
00100 {
00101 ind_printf (0, fp, a, b, c, d, e, f, g);
00102 }
00103
00104
00105 void
00106 nice_printf (fp, a, b, c, d, e, f, g)
00107 FILE *fp;
00108 char *a;
00109 long b, c, d, e, f, g;
00110 {
00111 ind_printf (1, fp, a, b, c, d, e, f, g);
00112 }
00113 #define SPRINTF(x,a,b,c,d,e,f,g) sprintf(x,a,b,c,d,e,f,g)
00114
00115 #else
00116
00117 #define SPRINTF(x,a,b,c,d,e,f,g) vsprintf(x,a,ap)
00118
00119 void
00120 margin_printf(FILE *fp, const char *fmt, ...)
00121 {
00122 va_list ap;
00123 va_start(ap,fmt);
00124 ind_printf(0, fp, fmt, ap);
00125 va_end(ap);
00126 }
00127
00128 void
00129 nice_printf(FILE *fp, const char *fmt, ...)
00130 {
00131 va_list ap;
00132 va_start(ap,fmt);
00133 ind_printf(1, fp, fmt, ap);
00134 va_end(ap);
00135 }
00136 #endif
00137
00138 #define max_line_len c_output_line_length
00139
00140
00141
00142
00143
00144
00145
00146
00147
00148
00149 static char *output_buf;
00150 static char *next_slot;
00151 static char *string_start;
00152
00153 static char *word_start = NULL;
00154 static int cursor_pos = 0;
00155 static int In_string = 0;
00156
00157 void
00158 np_init(Void)
00159 {
00160 next_slot = output_buf = Alloc(MAX_OUTPUT_SIZE);
00161 memset(output_buf, 0, MAX_OUTPUT_SIZE);
00162 }
00163
00164 static char *
00165 #ifdef KR_headers
00166 adjust_pointer_in_string(pointer)
00167 register char *pointer;
00168 #else
00169 adjust_pointer_in_string(register char *pointer)
00170 #endif
00171 {
00172 register char *s, *s1, *se, *s0;
00173
00174
00175 s1 = string_start ? string_start : output_buf;
00176 for(s = s1; s < pointer; s++) {
00177 s0 = s1;
00178 s1 = s;
00179 if (*s == '\\') {
00180 se = s++ + 4;
00181 if (se > pointer)
00182 break;
00183 if (*s < '0' || *s > '7')
00184 continue;
00185 while(++s < se)
00186 if (*s < '0' || *s > '7')
00187 break;
00188 --s;
00189 }
00190 }
00191 return s0 - 1;
00192 }
00193
00194
00195
00196
00197 static void
00198 #ifdef KR_headers
00199 fwd_strcpy(t, s)
00200 register char *t;
00201 register char *s;
00202 #else
00203 fwd_strcpy(register char *t, register char *s)
00204 #endif
00205 { while(*t++ = *s++); }
00206
00207
00208
00209
00210
00211
00212
00213
00214 #define isident(x) (Tr[x] & 1)
00215 #define isntident(x) (!Tr[x])
00216
00217 static void
00218 #ifdef KR_headers
00219 ind_printf (use_indent, fp, a, b, c, d, e, f, g)
00220 int use_indent;
00221 FILE *fp;
00222 char *a;
00223 long b, c, d, e, f, g;
00224 #else
00225 ind_printf (int use_indent, FILE *fp, const char *a, va_list ap)
00226 #endif
00227 {
00228 extern int max_line_len;
00229 extern FILEP c_file;
00230 extern char tr_tab[];
00231 register char *Tr = tr_tab;
00232 int ch, cmax, inc, ind;
00233 static int extra_indent, last_indent, set_cursor = 1;
00234
00235 cursor_pos += indent - last_indent;
00236 last_indent = indent;
00237 SPRINTF (next_slot, a, b, c, d, e, f, g);
00238
00239 if (fp != c_file) {
00240 fprintf (fp,"%s", next_slot);
00241 return;
00242 }
00243
00244 do {
00245 char *pointer;
00246
00247
00248
00249 if (set_cursor) {
00250 ind = indent <= MAX_INDENT
00251 ? indent
00252 : MIN_INDENT + indent % (MAX_INDENT - MIN_INDENT);
00253 cursor_pos = extra_indent;
00254 if (use_indent)
00255 cursor_pos += ind;
00256 set_cursor = 0;
00257 }
00258 if (in_comment) {
00259 cmax = max_line_len + 32;
00260 for (pointer = next_slot; *pointer && *pointer != '\n' &&
00261 cursor_pos <= cmax; pointer++)
00262 cursor_pos++;
00263 }
00264 else
00265 for (pointer = next_slot; *pointer && *pointer != '\n' &&
00266 cursor_pos <= max_line_len; pointer++) {
00267
00268
00269
00270 if (In_string) {
00271 switch(*pointer) {
00272 case '\\':
00273 if (++cursor_pos > max_line_len) {
00274 cursor_pos -= 2;
00275 --pointer;
00276 goto overflow;
00277 }
00278 ++pointer;
00279 break;
00280 case '"':
00281 In_string = 0;
00282 word_start = 0;
00283 }
00284 }
00285 else switch (*pointer) {
00286 case '"':
00287 if (cursor_pos + 5 > max_line_len) {
00288 word_start = 0;
00289 --pointer;
00290 goto overflow;
00291 }
00292 In_string = 1;
00293 string_start = word_start = pointer;
00294 break;
00295 case '\'':
00296 if (pointer[1] == '\\')
00297 if ((ch = pointer[2]) >= '0' && ch <= '7')
00298 for(inc = 3; pointer[inc] != '\''
00299 && ++inc < 5;);
00300 else
00301 inc = 3;
00302 else
00303 inc = 2;
00304 if (pointer[inc] != '\'')
00305 fatalstr("Bad character constant %.10s",
00306 pointer);
00307 if ((cursor_pos += inc) > max_line_len) {
00308 cursor_pos -= inc;
00309 word_start = 0;
00310 --pointer;
00311 goto overflow;
00312 }
00313 word_start = pointer;
00314 pointer += inc;
00315 break;
00316 case '\t':
00317 cursor_pos = 8 * ((cursor_pos + 8) / 8) - 1;
00318 break;
00319 default: {
00320
00321
00322
00323
00324
00325 if (word_start) {
00326 if (isntident(*(unsigned char *)pointer))
00327 word_start = NULL;
00328 }
00329 else if (isident(*(unsigned char *)pointer))
00330 word_start = pointer;
00331 break;
00332 }
00333 }
00334 cursor_pos++;
00335 }
00336 overflow:
00337 if (*pointer == '\0') {
00338
00339
00340
00341
00342 next_slot = pointer;
00343 break;
00344 } else {
00345 char last_char;
00346 int in_string0 = In_string;
00347
00348
00349
00350
00351
00352
00353
00354 if (*pointer == '\n')
00355 in_define = 0;
00356 else if (word_start && word_start > output_buf)
00357 if (In_string)
00358 if (string_start && pointer - string_start < 5)
00359 pointer = string_start - 1;
00360 else {
00361 pointer = adjust_pointer_in_string(pointer);
00362 string_start = 0;
00363 }
00364 else if (word_start == string_start
00365 && pointer - string_start >= 5) {
00366 pointer = adjust_pointer_in_string(next_slot);
00367 In_string = 1;
00368 string_start = 0;
00369 }
00370 else
00371 pointer = word_start - 1;
00372 else if (cursor_pos > max_line_len) {
00373 #ifndef ANSI_Libraries
00374 extern char *strchr();
00375 #endif
00376 if (In_string) {
00377 pointer = adjust_pointer_in_string(pointer);
00378 if (string_start && pointer > string_start)
00379 string_start = 0;
00380 }
00381 else if (strchr("&*+-/<=>|", *pointer)
00382 && strchr("!%&*+-/<=>^|", pointer[-1])) {
00383 pointer -= 2;
00384 if (strchr("<>", *pointer))
00385 pointer--;
00386 }
00387 else {
00388 if (word_start)
00389 while(isident(*(unsigned char *)pointer))
00390 pointer++;
00391 pointer--;
00392 }
00393 }
00394 last_char = *pointer;
00395 write_indent(fp, use_indent, extra_indent, output_buf, pointer);
00396 next_slot = output_buf;
00397 if (In_string && !string_start && Ansi == 1 && last_char != '\n')
00398 *next_slot++ = '"';
00399 fwd_strcpy(next_slot, pointer + 1);
00400
00401
00402
00403 if (last_char == '\n') {
00404 if (In_string)
00405 last_was_newline = 0;
00406 else {
00407 last_was_newline = 1;
00408 extra_indent = 0;
00409 sharp_line = gflag1;
00410 }
00411 }
00412 else {
00413 extra_indent = TOO_LONG_INDENT;
00414 if (In_string && !string_start) {
00415 if (Ansi == 1) {
00416 fprintf(fp, gflag1 ? "\"\\\n" : "\"\n");
00417 use_indent = 1;
00418 last_was_newline = 1;
00419 }
00420 else {
00421 fprintf(fp, "\\\n");
00422 last_was_newline = 0;
00423 }
00424 In_string = in_string0;
00425 }
00426 else {
00427 if (in_define)
00428 putc('\\', fp);
00429 putc ('\n', fp);
00430 last_was_newline = 1;
00431 }
00432 }
00433
00434 if (In_string && Ansi != 1 && !string_start)
00435 cursor_pos = 0;
00436 else
00437 set_cursor = 1;
00438
00439 string_start = word_start = NULL;
00440
00441 }
00442
00443 } while (*next_slot);
00444
00445 }