OSDN Git Service

updated macro.
[putex/putex.git] / src / texsourc / tex0.c
1 #ifdef _WINDOWS
2   #define NOCOMM
3   #define NOSOUND
4   #define NODRIVERS
5   #define STRICT
6   #pragma warning(disable:4115) // kill rpcasync.h complaint
7   #include <windows.h>
8   #define MYLIBAPI __declspec(dllexport)
9 #endif
10
11 #include "texwin.h"
12
13 #pragma warning(disable:4996)
14 #pragma warning(disable:4131) // old style declarator
15 #pragma warning(disable:4135) // conversion between different integral types 
16 #pragma warning(disable:4127) // conditional expression is constant
17
18 #include <setjmp.h>
19
20 #define EXTERN extern
21
22 #include "texd.h"
23
24 #ifdef IGNORED
25 static void winerror (char * message)
26 {
27   (void) MessageBox(NULL, message, "YandYTeX.DLL", MB_ICONSTOP | MB_OK);
28 }
29 #endif
30
31 /* *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** */
32 void append_char (ASCII_code c)
33 {
34   str_pool[pool_ptr] = c;
35   incr(pool_ptr);
36 }
37 void print_err (const char * s)
38 {
39   if (interaction == error_stop_mode);
40     print_nl("! ");
41   print_string(s);
42 }
43 void tex_help (unsigned int n, ...)
44 {
45   unsigned int i;
46   va_list help_arg;
47
48   if (n > 6) n = 6;
49   help_ptr = n;
50   va_start(help_arg, n);
51   for (i = n - 1; i > n - 1; --i)
52     help_line[i] = va_arg(help_arg, char *);
53   va_end(help_arg);
54 }
55 /* *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** */
56
57 /* *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** */
58 // print newline
59 /* sec 0058 */
60 void print_ln (void)
61 {
62   switch (selector) {
63     case term_and_log:
64       {
65         show_char('\n');
66         term_offset = 0;
67         (void) putc ('\n', log_file);
68         file_offset = 0;
69       }
70       break;
71     case log_only:
72       {
73         (void) putc ('\n',  log_file);
74         file_offset = 0;
75       }
76       break;
77     case term_only:
78       {
79         show_char('\n');
80         term_offset = 0;
81       }
82       break;
83     case no_print:
84     case pseudo:
85     case new_string:
86       ;
87       break;
88     default:
89       (void) putc ('\n', write_file[selector]);
90       break;
91   }
92 }
93 /* sec 0059 */
94 void print_char_ (ASCII_code s)
95 {
96   if (s == new_line_char)
97     if (selector < pseudo) {
98       print_ln();
99       return;
100     }
101   switch (selector) {
102     case term_and_log:
103       {
104         (void) show_char(Xchr(s));
105         incr(term_offset);
106         (void) putc(Xchr(s), log_file);
107         incr(file_offset);
108         if (term_offset == max_print_line) {
109           show_char('\n');
110           term_offset = 0;
111         }
112         if (file_offset == max_print_line) {
113           (void) putc ('\n', log_file);
114           file_offset = 0;
115         }
116       }
117       break;
118     case log_only:
119       {
120         (void) putc(Xchr(s), log_file);
121         incr(file_offset);
122         if (file_offset == max_print_line) print_ln();
123       }
124       break;
125     case term_only:
126       {
127         (void) show_char(Xchr(s));
128         incr(term_offset); 
129         if (term_offset == max_print_line) print_ln();
130       }
131       break;
132     case no_print:
133       ;
134       break;
135     case pseudo:
136       if (tally < trick_count)
137         trick_buf[tally % error_line]= s;
138       break;
139     case new_string:
140       {
141 #ifdef ALLOCATESTRING
142         if (pool_ptr + 1 > current_pool_size) {
143           str_pool = realloc_str_pool (increment_pool_size);
144         }
145         if (pool_ptr < current_pool_size) {
146           str_pool[pool_ptr]= s;
147           incr(pool_ptr);
148         }
149 #else
150         if (pool_ptr < pool_size) {
151           str_pool[pool_ptr]= s;
152           incr(pool_ptr);
153         }
154 #endif
155       }
156       break; 
157     default: 
158       (void) putc(Xchr(s), write_file[selector]);
159       break; 
160   }
161   incr(tally);
162 }
163 /* sec 0059 */
164 /* This could be made more efficient using fputs ? ... bkph */
165 void print_ (integer s)
166 {
167   pool_pointer j;
168   integer nl;
169   if (s >= str_ptr) s = 259; /* ??? */
170   else if (s < 256)
171     if (s < 0) s = 259; /* ??? */
172     else {
173       if (selector > pseudo){
174         print_char(s);
175         return;
176       }
177       if ((s == new_line_char))
178         if (selector < 20) {
179           print_ln();
180           return;
181         }
182       nl = new_line_char; /* save eol */
183       new_line_char = -1; 
184 /* *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** */
185 /*    if (!show_in_hex && s < 256)  */      /* show control chars also ?? */
186       if (!show_in_hex && s < 256 && s >= 32) {      /* 94/Jan/26 */
187 /*        following added 1996/Jan/20 */
188         if (show_in_dos && s > 127) {     /* translate ANSI to DOS 850 */
189           if (wintodos[s-128] > 0) print_char (wintodos[s-128]);
190           else {              /* print in hex after all */
191             j = str_start[s]; 
192             while(j < str_start[s + 1]){
193               print_char(str_pool[j]); 
194               incr(j); 
195             } 
196           }
197         } else print_char(s);       /* don't translate to hex */
198       } else {                  /* not just a character */
199 /* *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** */
200         j = str_start[s]; 
201         while(j < str_start[s + 1]){
202           print_char(str_pool[j]); 
203           incr(j); 
204         } 
205       }
206       new_line_char = nl; /* restore eol */
207       return; 
208     }
209 /*  we get here with s > 256 - i.e. not a single character */
210   j = str_start[s]; 
211   while(j < str_start[s + 1]){
212     print_char(str_pool[j]); 
213     incr(j); 
214   }
215
216 void print_string_ (unsigned char *s)
217 {
218   while (*s > 0) print_char(*s++);
219 }
220 /* sec 0060 */
221 // print string number s from string pool by calling print_
222 void slow_print_ (integer s)
223 {
224   pool_pointer j;
225   if ((s >= str_ptr) || (s < 256)) print(s);
226   else {
227     j = str_start[s];
228     while (j < str_start[s + 1]) {
229 //    if (str_pool[j]>= 128) print(str_pool[j]-128); // debugging only
230 //    if (str_pool[j]== 0) print(36); // debugging only
231       print(str_pool[j]);
232       incr(j);
233     }
234   }
235 }
236 /* sec 0062 */
237 // print newline followed by string number s (unless at start of line)
238 void print_nl_ (char * s)
239 {
240   if (((term_offset > 0) && (odd(selector))) ||
241       ((file_offset > 0) && (selector >= log_only)))
242     print_ln();
243   print_string(s);
244 }
245 /* sec 0063 */
246 // print string number s preceded by escape character
247 void print_esc_ (char * s)
248 {
249   integer c;
250   c = escape_char;
251   if (c >= 0)
252     if (c < 256) print(c);
253   //slow_print(s);
254   print_string(s);
255
256 /* sec 0064 */
257 void print_the_digs_ (eight_bits k)
258 {
259   while (k > 0) {
260     decr(k);
261     if (dig[k]< 10)
262       print_char('0' + dig[k]);
263     else
264       print_char('A' + dig[k]);
265   }
266 }
267 /* sec 0065 */
268 void print_int_ (integer n)
269 {
270   char k;
271   integer m;
272   k = 0;
273   if (n < 0) {
274     print_char('-');
275     if (n > -100000000L)
276       n = - (integer) n;
277     else {
278       m = -1 - n;
279       n = m / 10;
280       m =(m % 10)+ 1;
281       k = 1;
282       if (m < 10)
283         dig[0]= (char) m;
284       else {
285         dig[0]= 0;
286         incr(n);
287       }
288     }
289   }
290   do {
291     dig[k]= (char) (n % 10);
292     n = n / 10;
293     incr(k);
294   } while(!(n == 0));
295   print_the_digs(k);
296 }
297 /* sec 0262 */
298 void print_cs_ (integer p)
299 {
300   if (p < 514)       /* if p < hash_base then ... p.262 */
301   if (p >= 257)        /* if p > single_base then ... p.262 */
302   if (p == 513)        /* if p = null_cs then ... p.262 */
303   {
304     print_esc("csname");
305     print_esc("endcsname");
306     print_char(' ');
307   } else {
308     //print_esc(p - 257);   /* p - single_base */
309     print_esc("");print(p - 257);
310 /*  if cat_code(p - single_base) = letter then ... p.262 */
311     if (eqtb[(hash_size + 1883) + p - 257].hh.v.RH == 11)
312     print_char(' ');
313   } 
314   else if (p < 1)
315     print_esc("IMPOSSIBLE.");
316   else print(p - 1); 
317   else if (p >= (hash_size + 781)) /* undefined_control_sequence */
318     print_esc("IMPOSSIBLE.");
319   else if ((hash[p].v.RH >= str_ptr)) 
320     print_esc("NONEXISTENT.");
321   else {
322     //print_esc(hash[p].v.RH); 
323     print_esc(""); print(hash[p].v.RH);
324     print_char(32);     /*    */
325   }
326 }
327 /* sec 0263 */
328 void sprint_cs_(halfword p)
329
330   if (p < 514)       /* if p < hash_base then ... p.263 */
331   if (p < 257)       /* if p < single_base then ... p.263 */
332     print(p - 1);     /* print (p - active_base); */
333   else if (p < 513)      /* else if p < null_cs then ... */
334     //print_esc(p - 257); /* print (p - single_base); */
335   {print_esc(""); print(p-257);}
336   else {
337     print_esc("csname");
338     print_esc("endcsname");
339   } 
340   else //print_esc(hash[p].v.RH); 
341   {
342     print_esc(""); print(hash[p].v.RH);
343   }
344
345 /* sec 0518 */
346 /* ! I can't find file `  c:/foo/  accents  .tex  '. */
347 void print_file_name_(integer n, integer a, integer e)
348
349 /*  sprintf(log_line, "\na %d n %d e %d\n", a, n, e); */
350 /*  show_line(log_line, 0); */
351 //  print_char(33);  // debugging only
352   slow_print(a); 
353 //  print_char(33);  // debugging only
354   slow_print(n); 
355 //  print_char(33);  // debugging only
356   slow_print(e); 
357 //  print_char(33);  // debugging only
358 }
359 /* sec 0699 */
360 void print_size_(integer s) 
361
362   if (s == 0)
363     print_esc("textfont");
364   else if (s == 16)
365     print_esc("scriptfont");
366   else
367     print_esc("scriptscriptfont");
368
369 /* sec 1355 */
370 void print_write_whatsit_(str_number s, halfword p)
371 {
372   //print_esc(s); 
373   print_esc(""); print(s);
374   if (mem[p + 1].hh.v.LH < 16)
375     print_int(mem[p + 1].hh.v.LH); 
376   else if (mem[p + 1].hh.v.LH == 16)
377     print_char('*');
378   else print_char('-');
379
380 #ifdef DEBUG
381 #endif /* DEBUG */
382 /* sec 0081 */
383 // called from itex.c and tex0.c only  NASTY NASTY!
384 // now uses uses non-local goto (longjmp) 1999/Nov/7
385 void jump_out (void) 
386 {
387   close_files_and_terminate(); 
388   {
389     int code;
390 #ifndef _WINDOWS
391     fflush(stdout); 
392 #endif
393     ready_already = 0;
394
395     if (trace_flag) show_line("EXITING at JUMPOUT\n", 0);
396
397 /* *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** */
398 //    if (endit(history) != 0) history = 2; /* 93/Dec/26 in local.c */
399 /* *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** */
400
401 //    abort_flag++;       // TURN OFF THE POWER ???
402
403     if ((history != 0) && (history != 1))
404       code = 1;
405     else
406       code = 0;
407     uexit(code); 
408 //    longjmp(jumpbuffer, code+1);
409   }
410 }
411 /* sec 0082 */
412 // deal with error by asking for user response 0-9, D, E, H, I, X, Q, R, S
413 // NOTE: this may JUMPOUT either via X, or because of too many errors
414 void error (void)
415 {/* 22 10 */ 
416   ASCII_code c; 
417   integer s1, s2, s3, s4; 
418   if (history < 2) history = 2;
419
420   print_char('.');
421   show_context();
422
423   if (interaction == 3)
424     while (true) {
425 lab22:          /* loop */
426       clear_for_error_prompt();
427       {
428         ;
429         print_string("? ");
430         term_input(264, help_ptr);
431       } 
432       if (last == first) return;    // no input
433       c = buffer[first];        // analyze first letter typed
434       if (c >= 97)           // uppercase letter first
435         c = (unsigned char) (c - 32); 
436       switch (c) {
437         case '0':
438         case '1':
439         case '2':
440         case '3':
441         case '4':
442         case '5':
443         case '6':
444         case '7':
445         case '8':
446         case '9':
447           if (deletions_allowed) {
448             s1 = cur_tok; 
449             s2 = cur_cmd; 
450             s3 = cur_chr; 
451             s4 = align_state; 
452             align_state = 1000000L; 
453             OK_to_interrupt = false; 
454             if ((last > first + 1) && (buffer[first + 1]>= 48) && (buffer[first + 1]<= 57))
455               c = (unsigned char) (c * 10 + buffer[first + 1]- 48 * 11); 
456             else
457               c = (unsigned char) (c - 48);
458             while (c > 0) {
459               get_token();
460               decr(c);
461             }
462             cur_tok = s1;
463             cur_cmd = s2;
464             cur_chr = s3;
465             align_state = s4;
466             OK_to_interrupt = true;
467             help2("I have just deleted some text, as you asked.",
468                 "You can now delete more, or insert, or whatever.");
469             show_context();
470             goto lab22;     /* loop again */
471           } 
472           break; 
473           ;
474 #ifdef DEBUG
475         case 'D':
476           {
477             debug_help();
478             goto lab22;       /* loop again */
479           }
480           break; 
481 #endif /* DEBUG */
482         case 'E':
483           if (base_ptr > 0) {
484             edit_name_start = str_start[input_stack[base_ptr].name_field];
485             edit_name_length = str_start[input_stack[base_ptr].name_field + 1] - 
486               str_start[input_stack[base_ptr].name_field];
487             edit_line = line;
488             jump_out();
489 //            return;     // can drop through now 99/Oct/20
490           }
491           break;
492         case 'H':
493           {
494             if (use_err_help)
495             {
496               give_err_help();
497               use_err_help = false;
498             } else {
499               if (help_ptr == 0)
500                 help2("Sorry, I don't know how to help in this situation.",
501                     "Maybe you should try asking a human?");
502               do {
503                 decr(help_ptr); 
504                 print_string(help_line[help_ptr]);
505                 print_ln();
506               } while (!(help_ptr == 0));
507             }
508             help4("Sorry, I already gave what help I could...",
509                 "Maybe you should try asking a human?",
510                 "An error might have occurred before I noticed any problems.",
511                 "``If all else fails, read the instructions.''");
512             goto lab22; /* loop again */
513           }
514           break;
515         case 'I':
516           {
517             begin_file_reading();
518             if (last > first + 1)
519             {
520               cur_input.loc_field = first + 1;
521               buffer[first]= 32;
522             } else {
523               {
524                 ;
525                 print_string("insert>");
526                 term_input(276, 0);
527               }
528               cur_input.loc_field = first;
529             }
530             first = last;
531             cur_input.limit_field = last - 1;
532             return;
533           }
534           break;
535         case 'Q':
536         case 'R':
537         case 'S':
538         {
539           error_count = 0; 
540           interaction = 0 + c - 81; /* Q = 0, R = 1, S = 2, T = 3 */
541           print_string("OK, entering ");
542           switch(c){
543             case 81 :       /* Q */
544             {
545               print_esc("batchmode"); /*  */
546               decr(selector); 
547             } 
548             break; 
549             case 82 :       /* R */
550               print_esc("nonstopmode"); /*  */
551               break; 
552             case 83 :       /* S */
553               print_esc("scrollmode"); /*   */
554               break; 
555           } 
556           print_string("...");
557           print_ln(); 
558 #ifndef _WINDOWS
559           fflush(stdout); 
560 #endif
561           return; 
562         } 
563         break; 
564         case 88 :       /* X */
565         {
566           interaction = 2; 
567           jump_out();
568 //          return;     // can drop through now 99/Oct/20   
569         } 
570         break; 
571         default: 
572           ; 
573           break; 
574       }           /* end of switch analysing response character */
575       {
576         print_string("Type <return> to proceed, S to scroll future error messages,");
577         print_nl("R to run without stopping, Q to run quietly,");  /*  */
578         print_nl("I to insert something, ");  /*  */
579         if (base_ptr > 0) print_string("E to edit your file,");
580         if (deletions_allowed) print_nl("1 or ... or 9 to ignore the next 1 to 9 tokens of input,"); /*  */
581         print_nl("H for help, X to quit.");  /*  */
582       } 
583     }   /* end of while(true) loop */
584
585   incr(error_count); 
586   if (error_count == 100) {
587     print_nl("(That makes 100 errors; please try again.)");
588     history = 3; 
589     jump_out();
590 //    return;     // can drop through now 99/Oct/20   
591   } 
592   if (interaction > 0) decr(selector); 
593   if (use_err_help) {
594     print_ln(); 
595     give_err_help(); 
596   } 
597   else while(help_ptr > 0){
598     decr(help_ptr); 
599     print_nl(help_line[help_ptr]); 
600   } 
601   print_ln(); 
602   if (interaction > 0)incr(selector); 
603   print_ln(); 
604
605
606 void fatal_error_(char * s)
607 {
608   normalize_selector();
609   print_err("Emergency stop");
610   help1(s); 
611   {
612     if (interaction == 3)interaction = 2; 
613     if (log_opened){
614       error();
615     }
616     ;
617 #ifdef DEBUG
618     if (interaction > 0)debug_help(); 
619 #endif /* DEBUG */
620     history = 3; 
621     jump_out();
622 //    return;     // can drop through now 99/Oct/20   
623   } 
624 }
625 /* sec 0094 */
626 void overflow_(char * s, integer n)
627 {
628   normalize_selector();
629   print_err("TeX capacity exceeded, sorry[");
630   print_string(s); 
631   print_char('=');
632   print_int(n); 
633   print_char(']');
634   help2("If you really absolutely need more capacity,",
635       "you can ask a wizard to enlarge me."); 
636   if (! knuth_flag) {   /*  Additional comments 98/Jan/5 */
637     if (!strcmp(s, "pattern memory") && n == trie_size) {
638       sprintf(log_line, "\n  (Maybe use -h=... on command line in ini-TeX)\n");
639       show_line(log_line, 0);
640     } else if (!strcmp(s, "exception dictionary") && n == hyphen_prime) {
641       sprintf(log_line, "\n  (Maybe use -e=... on command line in ini-TeX)\n");
642       show_line(log_line, 0);
643     }
644   }
645   if (interaction == 3)
646     interaction = 2;
647   if (log_opened) {
648     error();
649   }
650   ;
651 #ifdef DEBUG
652   if (interaction > 0)
653     debug_help();
654 #endif
655   history = 3;
656   jump_out();
657 }
658 /* sec 0095 */
659 void confusion_(char * s)
660 {
661   normalize_selector(); 
662   if (history < 2) {
663     print_err("This can't happen(");
664     print_string(s); 
665     print_char(')');
666     help1("I'm broken. Please show this to someone who can fix can fix");
667   } else {
668     print_err("I can't go on meeting you like this");
669     help2("One of your faux pas seems to have wounded me deeply...",
670         "in fact, I'm barely conscious. Please fix it and try again.");
671   }
672   {
673     if (interaction == 3)
674       interaction = 2;
675     if (log_opened) {
676       error();
677     }
678     ;
679 #ifdef DEBUG
680     if (interaction > 0)
681       debug_help();
682 #endif
683     history = 3;
684     jump_out();
685   }
686 }
687 /* sec 0037 */
688 bool init_terminal (void) 
689 {/* 10 */
690   register bool Result; 
691   int flag;
692   t_open_in(); 
693
694   if (last > first) {
695     cur_input.loc_field = first; 
696     while((cur_input.loc_field < last) && (buffer[cur_input.loc_field]== ' '))
697       incr(cur_input.loc_field);    // step over initial white space
698     if (cur_input.loc_field < last){
699       Result = true; 
700       return Result;    // there is an input file name
701     } 
702   } 
703
704 //  failed to find input file name
705   while(true){
706     ; 
707 #ifdef _WINDOWS
708     flag = ConsoleInput("**", "Please type a file name or a control sequence\r\n(or ^z to exit)", (char *) &buffer[first]);
709     last = first + strlen((char *) &buffer[first]); /* -1 ? */
710 //    may need to be more elaborate see input_line in texmf.c
711 #else
712     (void) fputs("**", stdout);
713     fflush(stdout); 
714     flag = input_ln(stdin, true);
715 #endif
716     if (! flag){
717       show_char('\n');
718       show_line("! End of file on the terminal... why?\n", 1);
719       Result = false;
720       return Result;
721     }
722
723     cur_input.loc_field = first;
724     while ((cur_input.loc_field < last) && (buffer[cur_input.loc_field]== ' '))
725       incr(cur_input.loc_field);    // step over intial white space
726     if (cur_input.loc_field < last) {
727       Result = true;
728       return Result;    // there is an input file name
729     } 
730     sprintf(log_line, "%s\n", "Please type the name of your input file.");
731     show_line(log_line, 1);
732   }
733 }
734 /* sec 0043 */
735 // Make string from str_start[str_ptr]to pool_ptr
736 str_number make_string (void)
737 {
738   register str_number Result; 
739 /* *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** */
740 #ifdef ALLOCATESTRING
741   if (str_ptr == current_max_strings)
742     str_start = realloc_str_start(increment_max_strings);
743   if (str_ptr == current_max_strings) {
744 //  printf("**********MAKESTRING**********");   // debugging only
745     overflow("number of strings", current_max_strings - init_str_ptr); /* 97/Mar/9 */
746     return 0;     // abort_flag set
747   }
748 #else
749   if (str_ptr == max_strings) {
750     overflow("number of strings", max_strings - init_str_ptr); /* number of strings */
751     return 0;     // abort_flag set
752   }
753 #endif
754   incr(str_ptr); 
755   str_start[str_ptr] = pool_ptr;
756   Result = str_ptr - 1;
757   return Result;
758
759 /* sec 0044 */
760 bool str_eq_buf_ (str_number s, integer k)
761 {
762   register bool Result;
763   pool_pointer j;
764   bool result;
765   j = str_start[s];
766   while (j < str_start[s + 1]) {
767     if (str_pool[j]!= buffer[k])
768     {
769       result = false;
770       goto lab45;
771     } 
772     incr(j);
773     incr(k);
774   } 
775   result = true;
776 lab45: Result = result;
777   return Result; 
778
779 /* sec 0045 */
780 bool str_eq_str_ (str_number s, str_number t)
781 {
782   register bool Result;
783   pool_pointer j, k;
784   bool result;
785   result = false;
786   if ((str_start[s + 1] - str_start[s]) != (str_start[t + 1] - str_start[t]))
787     goto lab45;
788   j = str_start[s];
789   k = str_start[t];
790   while (j < str_start[s + 1]) {
791     if (str_pool[j] != str_pool[k])
792       goto lab45;
793     incr(j);
794     incr(k);
795   }
796   result = true;
797   lab45: Result = result;
798   return Result;
799 }
800 /* sec 0066 */
801 void print_two_(integer n)
802
803   n = abs(n) % 100;
804   print_char('0' + (n / 10));
805   print_char('0' + (n % 10));
806
807 /* sec 0067 */
808 void print_hex_(integer n)
809 {
810   char k;
811   k = 0;
812   print_char('"');
813   do {
814     dig[k] = (unsigned char) (n % 16);
815     n = n / 16;
816     incr(k);
817   } while (!(n == 0));
818   print_the_digs(k);
819 }
820 /* sec 0069 */
821 void print_roman_int_(integer n)
822 {
823   pool_pointer j, k;
824   nonnegative_integer u, v;
825   j = str_start[260]; /*  m2d5c2l5x2v5i */
826   v = 1000;
827   while (true) {
828     while (n >= v) {
829       print_char(str_pool[j]);
830       n = n - v;
831     } 
832     if (n <= 0)
833       return;
834     k = j + 2;
835     u = v / (str_pool[k - 1]- 48);
836     if (str_pool[k - 1]== 50)
837     {
838       k = k + 2;
839       u = u / (str_pool[k - 1]- 48);
840     }
841     if (n + u >= v)
842     {
843       print_char(str_pool[k]);
844       n = n + u;
845     } else {
846       j = j + 2;
847       v = v / (str_pool[j - 1]- 48);
848     }
849   }
850 }
851 /* sec 0070 */
852 void print_current_string (void)
853 {
854   pool_pointer j;
855   j = str_start[str_ptr];
856   while (j < pool_ptr) {
857     print_char(str_pool[j]);
858     incr(j);
859   }
860 }
861
862 int stringlength (int str_ptr)
863 {
864   int nstart, nnext;
865   nstart = str_start[str_ptr];
866   nnext = str_start[str_ptr + 1];
867   return (nnext - nstart) + 2;
868 }
869
870 char * add_string (char *s, int str_ptr)
871 {
872   int nstart, nnext, n;
873   nstart = str_start[str_ptr];
874   nnext = str_start[str_ptr + 1];
875   n = nnext - nstart;
876   memcpy(s, &str_pool[nstart], n);
877   s += n;
878   strcpy(s, "\r\n");
879   s += 2;
880   return s;
881 }
882
883 int addextrahelp=1;
884
885 // make one long \r\n separated string out of help lines 
886 // str_pool is packed_ASCII_code *
887
888 char * make_up_help_string (int nhelplines)
889 {
890   char * helpstring, *s;
891   int k, nlen=0;
892   
893 //  get length of help for this specific message
894   for (k = nhelplines-1; k >= 0; k--) {
895     //nlen += stringlength(help_line[k]);
896     nlen += strlen(help_line[k]);
897   }
898   nlen += 2;    // for blank line separator
899   if (addextrahelp) {
900     nlen += stringlength(265);
901     nlen += stringlength(266);
902     nlen += stringlength(267);
903     if (base_ptr > 0)nlen += stringlength(268);
904     if (deletions_allowed)nlen += stringlength(269);
905     nlen += stringlength(270);
906   }
907   helpstring = (char *) malloc(nlen+1);
908   s = helpstring;
909   for (k = nhelplines-1; k >= 0; k--) {
910     s = add_string(s, help_line[k]);
911   }
912   if (addextrahelp) {
913     strcpy(s, "\r\n");
914     s += 2;
915     s = add_string(s, 265);    /* Type <return> to proceed, S to scroll future error messages, */
916     s = add_string(s, 266);    /* R to run without stopping, Q to run quietly, */
917     s = add_string(s, 267);    /* I to insert something,  */
918     if (base_ptr > 0)s = add_string(s, 268);  /*  E to edit your file,  */
919     if (deletions_allowed)s = add_string(s,  269);  /* 1 or ... or 9 to ignore the next 1 to 9 tokens of input, */
920     s = add_string(s, 270);    /* H for help, X to quit. */
921   }
922   return helpstring;
923 }
924
925 char * make_up_query_string (int promptstr)
926 {
927   char *querystr;
928   int nstart, nnext, n;
929   char *s;
930   nstart = str_start[ promptstr];
931   nnext = str_start[ promptstr + 1];
932   n = nnext - nstart;
933   querystr = (char *) malloc(n + 1);
934   s = querystr;
935   memcpy(s, &str_pool[nstart], n);  
936   s += n;
937   *s = '\0';
938   return querystr;
939 }
940
941 // abort_flag set if input_line / ConsoleInput returns non-zero
942 // should set interrupt instead ???
943 // called from tex0.c, tex2.c, tex3.c
944
945 // void term_input(void)
946 void term_input (int promptstr, int nhelplines)
947
948   integer k;
949   int flag;
950   char * helpstring = NULL;
951   char * querystring = NULL;
952 //  if (nhelplines != 0) {
953 //    helpstring = make_up_help_string (nhelplines);
954 //    printf(helpstring);
955 //    free(helpstring);
956 //  }
957   show_line("\n", 0);    // force it to show what may be buffered up ???
958   helpstring = NULL;  
959 #ifdef _WINDOWS
960   if (promptstr != 0) querystring = make_up_query_string (promptstr);
961   if (nhelplines != 0) helpstring = make_up_help_string (nhelplines);
962   if (helpstring == NULL && querystring != NULL) {
963     if (strcmp(querystring, ": ") == 0)
964       helpstring = xstrdup("Please type another file name (or ^z to exit):");
965     else if (strcmp(querystring, "=>") == 0)    // from firm_up_the_line
966       helpstring = xstrdup("Please type <enter> to accept this line\r\nor type a replacement line");
967     else if (strcmp(querystring, "insert>") == 0) // from error() after "I"
968       helpstring = xstrdup("Please type something to insert here");
969     else if (strcmp(querystring, "") == 0)      // from read_toks
970       helpstring = xstrdup("Please type a control sequence");
971     else if (strcmp(querystring, "= ") == 0)    // from read_toks
972       helpstring = xstrdup("Please type a token");
973     else if (strcmp(querystring, "*") == 0)   // get_next
974       helpstring = xstrdup("Please type a control sequence\r\n(or ^z to exit)");
975 //    else if (strcmp(querystring, "**") == 0)  // init_terminal
976 //      helpstring = xstrdup("Please type a control sequence or a file name\r\n(or ^z to exit)");     
977 //    else if (strcmp(querystring, "? ") == 0)  // from error()
978 //      helpstring = xstrdup("Please type a character to select an action");
979   }
980   flag = ConsoleInput(querystring, helpstring, (char *) &buffer[first]);  // ???
981 //  flag == 0 means trouble --- EOF on terminal
982   if (querystring != NULL) free(querystring);
983   if (helpstring != NULL) free(helpstring);
984   helpstring = querystring = NULL;
985
986   last = first + strlen((char *) &buffer[first]); /* -1 ? */
987 //  flag = (last > first);
988 //  may need to be more elaborate see input_line in texmf.c ???
989 //  sprintf(log_line, "first %d last %d flag %d - %s",
990 //      first, last, flag, (char *) &buffer[first]);
991 //  winerror(log_line);
992 #else
993   fflush(stdout); 
994   flag = input_ln(stdin, true);
995 #endif
996   if (! flag){
997     fatal_error("End of file on the terminal!"); /*  */
998     return;         // abort_flag set
999   }
1000   term_offset = 0; 
1001 #ifdef _WINDOWS
1002 // echo what was typed into Console buffer also
1003   if (last != first)
1004     {register integer for_end; k = first; for_end = last - 1;
1005   if (k <=  for_end) do
1006     print(buffer[k]); 
1007   while(k++ < for_end);
1008     } 
1009   print_ln(); 
1010 #else
1011   decr(selector);     // shut off echo
1012   if (last != first)
1013     {register integer for_end; k = first; for_end = last - 1;
1014   if (k <=  for_end) do
1015     print(buffer[k]); 
1016   while(k++ < for_end);
1017     } 
1018   print_ln(); 
1019   incr(selector);     // reset selector again
1020 #endif
1021 }
1022 /* sec 0091 */
1023 void int_error_ (integer n)
1024 {
1025   print_string(" (");
1026   print_int(n);
1027   print_char(')');
1028   error();
1029 }
1030 /* sec 0092 */
1031 void normalize_selector (void)
1032 {
1033   if (log_opened)
1034     selector = 19;
1035   else
1036     selector = 17;
1037   if (job_name == 0)
1038     open_log_file();
1039   if (interaction == 0)
1040     decr(selector);
1041 }
1042 /* sec 0098 */
1043 void pause_for_instructions (void)
1044 {
1045    if (OK_to_interrupt) {
1046     interaction = 3;
1047     if ((selector == 18)||(selector == 16))
1048       incr(selector);
1049     print_err("Interruption");
1050     help3("You rang?",
1051         "Try to insert some instructions for me (e.g.,`I\\showlists'),",
1052         "unless you just want to quit by typing `X'.");
1053     deletions_allowed = false;
1054     error();
1055     deletions_allowed = true;
1056     interrupt = 0;
1057   }
1058 }
1059 /* sec 0100 */
1060 integer half_(integer x)
1061 {
1062   register integer Result;
1063   if (odd(x))
1064   Result =(x + 1)/ 2;
1065   else Result = x / 2;
1066   return Result;
1067 }
1068 /* sec 0102 */
1069 scaled round_decimals_(small_number k)
1070 {
1071   register scaled Result;
1072   integer a;
1073   a = 0;
1074   while (k > 0) {
1075     decr(k);
1076     a = (a + dig[k]* 131072L) / 10; /* 2^17 */
1077   }
1078   Result =(a + 1)/ 2;
1079   return Result;
1080 }
1081 /* sec 0103 */
1082 /* This has some minor speedup changes - no real advantage probably ... */
1083 void print_scaled_(scaled s)
1084
1085   scaled delta;
1086   if (s < 0)
1087   {
1088     print_char('-');
1089     s = - (integer) s;
1090   }
1091   print_int(s / 65536L);
1092   print_char('.');
1093   s = 10 * (s % 65536L) + 5;
1094   delta = 10;
1095   do {
1096     if (delta > 65536L)
1097       s = s - 17232; /* 2^15 - 50000 - rounding */
1098     print_char('0' + (s / 65536L));
1099     s = 10 * (s % 65536L);
1100     delta = delta * 10;
1101   } while (!(s <= delta));
1102 }
1103 /* sec 0105 */
1104 scaled mult_and_add_(integer n, scaled x, scaled y, scaled maxanswer)
1105 {
1106   register scaled Result;
1107   if (n < 0)
1108   {
1109     x = - (integer) x;
1110     n = - (integer) n;
1111   }
1112   if (n == 0)
1113     Result = y;
1114   else if (((x <= (maxanswer - y) / n) && (- (integer) x <= (maxanswer + y) / n)))
1115     Result = n * x + y; 
1116   else {
1117     arith_error = true;
1118     Result = 0;
1119   }
1120   return Result;
1121 }
1122 /* sec 0106 */
1123 scaled x_over_n_(scaled x, integer n)
1124 {
1125   register scaled Result;
1126   bool negative;
1127   negative = false;
1128   if (n == 0)
1129   {
1130     arith_error = true;
1131     Result = 0;
1132     tex_remainder = x;
1133   } else {
1134     if (n < 0)
1135     {
1136       x = - (integer) x;
1137       n = - (integer) n;
1138       negative = true;
1139     }
1140     if (x >= 0)
1141     {
1142       Result = x / n;
1143       tex_remainder = x % n;
1144     } else {
1145       Result = - (integer) ((- (integer) x)/ n);
1146       tex_remainder = - (integer) ((- (integer) x)% n);
1147     }
1148   }
1149   if (negative)
1150     tex_remainder = - (integer) tex_remainder;
1151   return Result;
1152 }
1153 /* sec 0107 */
1154 scaled xn_over_d_(scaled x, integer n, integer d)
1155 {
1156   register scaled Result;
1157   bool positive;
1158   nonnegative_integer t, u, v;
1159   if (x >= 0)
1160     positive = true; 
1161   else {
1162     x = - (integer) x;
1163     positive = false;
1164   }
1165 /*  t =(x % 32768L)* n;  */
1166   t =(x & 32767L) * n;
1167 /*  u =(x / 32768L)* n +(t / 32768L);  */
1168   u =(x >> 15) * n + (t >> 15); 
1169 /*  v =(u % d)* 32768L +(t % 32768L);  */
1170   v =((u % d) << 15) + (t & 32767L); 
1171   if (u / d >= 32768L)
1172     arith_error = true; 
1173 /*  else u = 32768L *(u / d)+(v / d);  */ 
1174   else u =((u / d) << 15) + (v / d); 
1175   if (positive)
1176   {
1177     Result = u;
1178     tex_remainder = v % d;
1179   } else {
1180     Result = - (integer) u;
1181     tex_remainder = - (integer)(v % d);
1182   }
1183   return Result;
1184 }
1185 /* sec 0108 */
1186 halfword badness_(scaled t, scaled s)
1187 {
1188   register halfword Result;
1189   integer r;
1190   if (t == 0)
1191     Result = 0; 
1192   else if (s <= 0)
1193     Result = 10000; 
1194   else {
1195     if (t <= 7230584L)
1196       r = (t * 297) / s; 
1197     else if (s >= 1663497L)
1198       r = t / (s / 297);
1199     else
1200       r = t;
1201     if (r > 1290)
1202       Result = 10000; 
1203 /*    safe to assume that r is positive ? */
1204 /*    else Result =(r * r * r + 131072L)/ 262144L;  */
1205     else Result = (r * r * r + 131072L) >> 18;  /* 2^17 */
1206   }
1207   return Result;
1208 }
1209
1210 #ifdef DEBUG
1211 void print_word_(memory_word w)
1212
1213   print_int(w.cint); 
1214   print_char(' ');
1215   print_scaled(w.cint); 
1216   print_char(' ');
1217   print_scaled(round(65536L * w.gr));
1218   print_ln();
1219   print_int(w.hh.v.LH);
1220   print_char('=');
1221   print_int(w.hh.b0);
1222   print_char(':');
1223   print_int(w.hh.b1);
1224   print_char(';');
1225   print_int(w.hh.v.RH);
1226   print_char(' ');
1227   print_int(w.qqqq.b0); 
1228   print_char(':');
1229   print_int(w.qqqq.b1); 
1230   print_char(':');
1231   print_int(w.qqqq.b2); 
1232   print_char(':');
1233   print_int(w.qqqq.b3);
1234
1235 /* need this version only if SHORTFONTINFO defined */
1236 void zprintfword(fmemoryword w)
1237 {
1238   print_int(w.cint);
1239   print_char(' ');
1240   print_scaled(w.cint);
1241   print_char(' ');
1242   print_scaled(round(65536L * w.gr));
1243   print_ln();
1244   print_int(w.hh.v.LH);
1245   print_char('=');
1246   print_int(w.hh.b0);
1247   print_char(':');
1248   print_int(w .hh.b1);
1249   print_char(';');
1250   print_int(w.hh.v.RH);
1251   print_char(' ');
1252   print_int(w.qqqq.b0);
1253   print_char(':');
1254   print_int(w.qqqq.b1);
1255   print_char(':');
1256   print_int(w.qqqq.b2);
1257   print_char(':');
1258   print_int(w.qqqq.b3);
1259 }
1260 #endif
1261
1262 void show_token_list_(integer p, integer q, integer l)
1263 {
1264   integer m, c;
1265   ASCII_code matchchr;
1266   ASCII_code n;
1267   matchchr = 35;
1268   n = 48;
1269   tally = 0;
1270 /* while (p<>null) and (tally<l) do l.6239 */
1271   while ((p != 0) && (tally < l)) {
1272     if (p == q)
1273     {
1274       first_count = tally;
1275       trick_count = tally + 1 + error_line - half_error_line;
1276       if (trick_count < error_line)
1277         trick_count = error_line;
1278     }
1279     if ((p < hi_mem_min) || (p > mem_end))
1280     {
1281       print_esc("CLOBBERED.");
1282       return;
1283     }
1284     if (mem[p].hh.v.LH >= 4095)
1285       print_cs(mem[p].hh.v.LH - 4095);
1286     else {
1287       m = mem[p].hh.v.LH / 256;
1288       c = mem[p].hh.v.LH % 256;
1289       if (mem[p].hh.v.LH < 0)
1290         print_esc("BAD.");
1291       else
1292         switch (m)
1293         {
1294           case 1:
1295           case 2:
1296           case 3:
1297           case 4:
1298           case 7:
1299           case 8:
1300           case 10:
1301           case 11:
1302           case 12:
1303             print(c);
1304             break;
1305           case 6:
1306             {
1307               print(c);
1308               print(c);
1309             }
1310             break;
1311           case 5:
1312             {
1313               print(matchchr);
1314               if (c <= 9)
1315                 print_char(c + '0');
1316               else {
1317                 print_char('!');
1318                 return;
1319               }
1320             }
1321             break;
1322           case 13:
1323             {
1324               matchchr = (ASCII_code) c;
1325               print(c);
1326               incr(n);
1327               print_char(n);
1328               if (n > 57)
1329                 return;
1330             }
1331             break;
1332           case 14:
1333             print_string("->");
1334             break;
1335           default:
1336             print_esc("BAD. ");
1337             break;
1338         }
1339     }
1340     p = mem[p].hh.v.RH; 
1341   } 
1342 /* if p<>null then print_esc("ETC."); l.6244 */
1343   if (p != 0)
1344     print_esc("ETC.");
1345 }
1346 /* sec 0306 */
1347 void runaway (void)
1348 {
1349   halfword p;
1350   if (scanner_status > 1)
1351   {
1352     print_nl("Runaway ");
1353     switch (scanner_status)
1354     {
1355       case 2:
1356         {
1357           print_string("definition");
1358           p = def_ref;
1359         }
1360         break;
1361       case 3:
1362         {
1363           print_string("argument");
1364           p = temp_head;
1365         }
1366         break;
1367       case 4:
1368         {
1369           print_string("preamble");
1370           p = hold_head;
1371         }
1372         break;
1373       case 5:
1374         {
1375           print_string("text");
1376           p = def_ref;
1377         }
1378         break;
1379     }
1380     print_char('?');
1381     print_ln();
1382 /*  p may be used without being initialized -- OK */
1383     show_token_list(mem[p].hh.v.RH, 0, error_line - 10); 
1384   }
1385 }
1386 /* sec 0120 */
1387 /* *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** */
1388 /* first try list of available nodes (avail != NULL)                   */
1389 /* then see if can go upwards (mem_end < mem_max)                      */
1390 /* then see if can go downwards (hi_mem_min > lo_mem_max)              */
1391 /* if not, extend memory at the top and grab from there --- new        */
1392 /* else fail ! paragraph 120                                           */
1393 /* *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** */
1394 halfword get_avail (void)
1395 {
1396   register halfword Result;
1397   halfword p;
1398   p = avail;
1399   if (p != 0) /* while p<>null do */
1400     avail = link(avail);
1401   else if (mem_end < mem_max) /* mem_end + 1 < mem_max ? NO */
1402   {
1403     incr(mem_end);
1404     p = mem_end;
1405   } else {
1406     decr(hi_mem_min);
1407     p = hi_mem_min;
1408 /* *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** */
1409     if (hi_mem_min <= lo_mem_max) {   /* have we run out in middle ? */
1410       incr(hi_mem_min);       /* undo the change */
1411 /*    realloc_main (0, mem_top/2); */ /* extend main memory at hi end */
1412       mem = realloc_main (0, mem_top / 2);  /* zzzaa = zmem = mem */
1413       if (mem == NULL) {
1414         return 0;
1415       }
1416 /* presumably now mem_end < mem_max - but need test in case allocation fails */
1417       if (mem_end >= mem_max) {
1418         runaway();
1419         overflow("main memory size", mem_max + 1 - mem_min); /* main memory size */
1420         return 0;           // abort_flag set
1421       }
1422       incr(mem_end);        /* then grab from new area */
1423       p = mem_end;          /* 1993/Dec/14 */
1424     }
1425 /* *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** */
1426   }
1427   mem[p].hh.v.RH = 0;       /* link(p) = null !!! */
1428   ;
1429 #ifdef STAT
1430   incr(dyn_used); 
1431 #endif /* STAT */
1432   Result = p; 
1433   return Result; 
1434
1435 /* sec 0123 */
1436 void flush_list_(halfword p)          /* paragraph 123 */
1437
1438   halfword q, r; 
1439   if (p != 0)              /* null !!! */
1440   {
1441     r = p;
1442     do {
1443       q = r;
1444       r = link(r);
1445       ;
1446 #ifdef STAT
1447       decr(dyn_used);
1448 #endif /* STAT */
1449     } while (!(r == 0));     /* r != null */
1450     link(q) = avail;
1451     avail = p;
1452   }
1453 }
1454 /* sec 0125 */
1455 halfword get_node_(integer s)
1456 {
1457   register halfword Result;
1458   halfword p;
1459   halfword q;
1460   integer r;
1461   integer t;
1462 lab20: p = rover;
1463   do {
1464       q = p + mem[p].hh.v.LH;
1465 /* *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** */
1466 /*    while((mem[q].hh.v.RH == 262143L)) { */ /* NO! */
1467       while ((mem[q].hh.v.RH == empty_flag)) {
1468 /* *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** */
1469         if (q == 0) {
1470 /* should never happen, since this field is reference count for zeroglue */
1471         }  /* debugging code 93/DEC/15 */ /* eventually remove */
1472 /* *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** */
1473         t = mem[q + 1].hh.v.RH;
1474         if (q == rover)
1475           rover = t;
1476         mem[t + 1].hh.v.LH = mem[q + 1].hh.v.LH;
1477         mem[mem[q + 1].hh.v.LH + 1].hh.v.RH = t;
1478         q = q + mem[q].hh.v.LH;
1479       }
1480       r = q - s;
1481       if (r > toint(p + 1)) 
1482       {
1483         mem[p].hh.v.LH = r - p;
1484         rover = p;
1485         goto lab40;
1486       }
1487       if (r == p)
1488         if (mem[p + 1].hh.v.RH != p)
1489         {
1490           rover = mem[p + 1].hh.v.RH;
1491           t = mem[p + 1].hh.v.LH;
1492           mem[rover + 1].hh.v.LH = t;
1493           mem[t + 1].hh.v.RH = rover;
1494           goto lab40;
1495         }
1496       mem[p].hh.v.LH = q - p;
1497       p = mem[p + 1].hh.v.RH;
1498   } while (!(p == rover));
1499   if (s == 1073741824L)    /* 2^30 - special case - merge adjacent */
1500   {
1501     Result = empty_flag;
1502 /* *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** */
1503     if (trace_flag)
1504       show_line("Merged adjacent multi-word nodes\n", 0);
1505 /* *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** */
1506     return Result;
1507   }
1508 /*  maybe try downward epxansion first instead ? */
1509   if (lo_mem_max + 2 < hi_mem_min)
1510 /*  if (lo_mem_max + 2 <= 262143L) */  /* NO! */
1511     if (lo_mem_max + 2 <= mem_bot + max_halfword)  /* silly ? flush 93/Dec/16 */
1512     {
1513 /*    if (hi_mem_min - lo_mem_max >= 1998) */
1514       if (hi_mem_min - lo_mem_max >= (block_size + block_size - 2))
1515 /*    t = lo_mem_max + 1000;  */
1516         t = lo_mem_max + block_size;
1517       else
1518         t = lo_mem_max + 1 +(hi_mem_min - lo_mem_max) / 2;
1519       p = mem[rover + 1].hh.v.LH;
1520       q = lo_mem_max;
1521       mem[p + 1].hh.v.RH = q;
1522       mem[rover + 1].hh.v.LH = q;
1523 /*    if (t > 262143L)   t = 262143L;  */ /* NO! */
1524       if (t > mem_bot + max_halfword)
1525         t = mem_bot + max_halfword;     /* silly ? flush 93/Dec/16 */
1526       mem[q + 1].hh.v.RH = rover;
1527       mem[q + 1].hh.v.LH = p;
1528       mem[q].hh.v.RH = empty_flag;
1529       mem[q].hh.v.LH = t - lo_mem_max; /* block size */
1530       lo_mem_max = t;
1531       mem[lo_mem_max].hh.v.RH = 0;
1532       mem[lo_mem_max].hh.v.LH = 0;
1533       rover = q;
1534       goto lab20;
1535     }
1536 /*  overflow("main memory size", mem_max + 1 - mem_min);  */ /* what used to happen! */
1537 /* *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** */
1538 /* we've run out of space in the middle for variable length blocks */
1539 /* try and add new block from below mem_bot *//* first check if space ! */
1540   if (mem_min - (block_size + 1) <= mem_start) {/* extend lower memory downwards */
1541 /*    realloc_main (mem_top/2, 0); */
1542     mem = realloc_main (mem_top/2 + block_size, 0);  /* zzzaa = zmem = mem */
1543     if (mem == NULL) {
1544       return 0;
1545     }
1546   }
1547 /*  if (trace_flag) show_line("Extending downwards by %d\n", block_size, 0); */
1548   if (mem_min - (block_size + 1) <= mem_start) { /* check again */
1549     if (trace_flag) {
1550       sprintf(log_line, "mem_min %d, mem_start %d, block_size %d\n", mem_min, mem_start, block_size);
1551       show_line(log_line, 0);
1552     }
1553     overflow("main memory size", mem_max + 1 - mem_min); /* darn: allocation failed ! */
1554     return 0;     // abort_flag set
1555   }
1556 /* avoid function call in following ? */
1557   add_variable_space (block_size); /* now to be found in itex.c */
1558   goto lab20;         /* go try get_node again */
1559 /* *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** */
1560
1561   lab40: mem[r].hh.v.RH = 0; 
1562   ;
1563 #ifdef STAT
1564   var_used = var_used + s; 
1565 #endif /* STAT */
1566
1567 /*  if (trace_flag) {
1568     if (r == 0) show_line("r IS ZERO in ZGETNODE!\n", 0);
1569   } */      /* debugging code 93/dec/15 */
1570
1571   Result = r; 
1572   return Result; 
1573
1574
1575 void free_node_(halfword p, halfword s)
1576
1577   halfword q;
1578   mem[p].hh.v.LH = s;
1579   mem[p].hh.v.RH = empty_flag;
1580   q = mem[rover + 1].hh.v.LH;
1581   mem[p + 1].hh.v.LH = q;
1582   mem[p + 1].hh.v.RH = rover;
1583   mem[rover + 1].hh.v.LH = p;
1584   mem[q + 1].hh.v.RH = p;
1585   ;
1586 #ifdef STAT
1587   var_used = var_used - s; 
1588 #endif /* STAT */
1589
1590
1591 halfword new_null_box (void) 
1592 {
1593   register halfword Result;
1594   halfword p; 
1595   p = get_node(7);
1596   mem[p].hh.b0 = 0;
1597   mem[p].hh.b1 = 0;
1598   mem[p + 1].cint = 0;
1599   mem[p + 2].cint = 0;
1600   mem[p + 3].cint = 0;
1601   mem[p + 4].cint = 0;
1602   mem[p + 5].hh.v.RH = 0;
1603   mem[p + 5].hh.b0 = 0;
1604   mem[p + 5].hh.b1 = 0;
1605   mem[p + 6].gr = 0.0;
1606   Result = p;
1607   return Result;
1608
1609
1610 // @ A new rule node is delivered by the |new_rule| function. It
1611 //   makes all the dimensions ``running,'' so you have to change the
1612 //   ones that are not allowed to run.
1613
1614 halfword new_rule (void) 
1615 {
1616   register halfword Result;
1617   halfword p; 
1618   p = get_node(4);          /* rule_node_size */
1619   mem[p].hh.b0 = 2;       /* rule_node type */
1620   mem[p].hh.b1 = 0;       /* sub_type zero */
1621   mem[p + 1].cint = -1073741824L; /* -2^30 null_flag width */
1622   mem[p + 2].cint = -1073741824L; /* -2^30 null_flag depth */
1623   mem[p + 3].cint = -1073741824L; /* -2^30 null_flag height */
1624   Result = p; 
1625   return Result; 
1626
1627
1628 // @ The |new_ligature| function creates a ligature node having given
1629 //   contents of the |font|, |character|, and |lig_ptr| fields.
1630
1631 halfword new_ligature_(quarterword f, quarterword c, halfword q)
1632 {
1633   register halfword Result; 
1634   halfword p; 
1635   p = get_node(2);      /* small_node_size */
1636   mem[p].hh.b0 = 6;   /* ligature_node type */
1637   mem[p + 1].hh.b0 = f; /* font */
1638   mem[p + 1].hh.b1 = c; /* character */
1639   mem[p + 1].hh.v.RH = q; /* pointer */
1640   mem[p].hh.b1 = 0;   /* subtype zero */
1641   Result = p; 
1642   return Result; 
1643
1644
1645 //  We also have a |new_lig_item| function, which returns a two-word
1646 //  node having a given |character| field. Such nodes are used for
1647 //  temporary processing as ligatures are being created.
1648
1649 halfword new_lig_item_(quarterword c)
1650 {
1651   register halfword Result;
1652   halfword p; 
1653   p = get_node(2);      /* small_node_size */
1654   mem[p].hh.b1 = c;   /* character */ 
1655   mem[p + 1].hh.v.RH = 0; /* lig_ptr(p):=null; */
1656   Result = p; 
1657   return Result; 
1658
1659
1660 halfword new_disc (void) 
1661 {
1662   register halfword Result; 
1663   halfword p; 
1664   p = get_node(2); 
1665   mem[p].hh.b0 = 7; 
1666   mem[p].hh.b1 = 0; 
1667   mem[p + 1].hh.v.LH = 0; /* pre_break(p):=null; */
1668   mem[p + 1].hh.v.RH = 0; /* post_break(p):=null; */
1669   Result = p; 
1670   return Result; 
1671
1672
1673 halfword new_math_(scaled w, small_number s)
1674 {
1675   register halfword Result;
1676   halfword p; 
1677   p = get_node(2); 
1678   mem[p].hh.b0 = 9; 
1679   mem[p].hh.b1 = s; 
1680   mem[p + 1].cint = w; 
1681   Result = p; 
1682   return Result; 
1683
1684
1685 halfword new_spec_(halfword p)
1686 {
1687   register halfword Result;
1688   halfword q; 
1689   q = get_node(4); 
1690   mem[q]= mem[p]; 
1691   mem[q].hh.v.RH = 0; 
1692   mem[q + 1].cint = mem[p + 1].cint; 
1693   mem[q + 2].cint = mem[p + 2].cint; 
1694   mem[q + 3].cint = mem[p + 3].cint; 
1695   Result = q; 
1696   return Result; 
1697
1698
1699 halfword new_param_glue_(small_number n)
1700 {
1701   register halfword Result; 
1702   halfword p; 
1703   halfword q; 
1704   p = get_node(2); 
1705   mem[p].hh.b0 = 10; 
1706   mem[p].hh.b1 = n + 1; /* conversion int to unsigned short */
1707   mem[p + 1].hh.v.RH = 0; 
1708   q = eqtb[(hash_size + 782) + n].hh.v.RH; /* gluebase + n */
1709   mem[p + 1].hh.v.LH = q; 
1710   incr(mem[q].hh.v.RH); 
1711   Result = p; 
1712   return Result; 
1713
1714
1715 halfword new_glue_(halfword q)
1716 {
1717   register halfword Result; 
1718   halfword p; 
1719   p = get_node(2); 
1720   mem[p].hh.b0 = 10; 
1721   mem[p].hh.b1 = 0; 
1722   mem[p + 1].hh.v.RH = 0; 
1723   mem[p + 1].hh.v.LH = q; 
1724   incr(mem[q].hh.v.RH); 
1725   Result = p; 
1726   return Result; 
1727
1728
1729 halfword new_skip_param_(small_number n)
1730 {
1731   register halfword Result; 
1732   halfword p; 
1733   temp_ptr = new_spec(eqtb[(hash_size + 782) + n].hh.v.RH); /* gluebase + n */
1734   p = new_glue(temp_ptr); 
1735   mem[temp_ptr].hh.v.RH = 0; 
1736   mem[p].hh.b1 = n + 1;   /* conversion int to unsigned short */
1737   Result = p; 
1738   return Result; 
1739
1740
1741 halfword new_kern_(scaled w)
1742 {
1743   register halfword Result;
1744   halfword p; 
1745   p = get_node(2); 
1746   mem[p].hh.b0 = 11; 
1747   mem[p].hh.b1 = 0; 
1748   mem[p + 1].cint = w; 
1749   Result = p; 
1750   return Result; 
1751
1752
1753 halfword new_penalty_(integer m)
1754 {
1755   register halfword Result; 
1756   halfword p; 
1757   p = get_node(2); 
1758   mem[p].hh.b0 = 12; 
1759   mem[p].hh.b1 = 0; 
1760   mem[p + 1].cint = m; 
1761   Result = p; 
1762   return Result; 
1763
1764
1765 #ifdef DEBUG
1766 void check_mem_(bool printlocs)
1767 {/* 31 32 */  
1768   halfword p, q; 
1769   bool clobbered; 
1770   {
1771     register integer for_end;
1772     p = mem_min;
1773     for_end = lo_mem_max;
1774     if (p <= for_end) do 
1775       freearr[p]= false;
1776     while (p++ < for_end);
1777   }
1778   {
1779     register integer for_end;
1780     p = hi_mem_min;
1781     for_end = mem_end;
1782     if (p <= for_end) do
1783       freearr[p]= false;
1784     while (p++ < for_end);
1785   }
1786   p = avail;
1787   q = 0;
1788   clobbered = false;
1789   while (p != 0) {    /* while p<>null do */
1790     if ((p > mem_end) || (p < hi_mem_min))
1791       clobbered = true;
1792     else if (freearr[p])
1793       clobbered = true;
1794     if (clobbered)
1795     {
1796       print_nl("AVAIL list clobbered at ");
1797       print_int(q);
1798       goto lab31;
1799     }
1800     freearr[p] = true;
1801     q = p;
1802     p = mem[q].hh.v.RH;
1803   }
1804 lab31:;
1805   p = rover;
1806   q = 0;        /* q:=null */
1807   clobbered = false;
1808   do {
1809       if ((p >= lo_mem_max) || (p < mem_min))
1810         clobbered = true;
1811       else if ((mem[p + 1].hh.v.RH >= lo_mem_max) || (mem[p + 1].hh.v.RH < mem_min))
1812         clobbered = true;
1813 /*    else if (!((mem[p].hh.v.RH == 262143L)) ||(mem[p].hh *//*NO!*/
1814     else if (!((mem[p].hh.v.RH == empty_flag)) ||
1815         (mem[p].hh .v.LH < 2) || 
1816         (p + mem[p].hh.v.LH > lo_mem_max) ||
1817         (mem[mem[p + 1].hh.v.RH + 1].hh.v.LH != p))
1818       clobbered = true;
1819     if (clobbered)
1820     {
1821       print_nl("Double-AVAIL list clobbered at ");
1822       print_int(q);
1823       goto lab32;
1824     } 
1825     {
1826       register integer for_end;
1827       q = p;
1828       for_end = p + mem[p].hh.v.LH - 1;
1829       if (q <= for_end) do 
1830       {
1831         if (freearr[q])
1832         {
1833           print_nl("Doubly free location at ");
1834           print_int(q);
1835           goto lab32;
1836         }
1837         freearr[q]= true;
1838       } while (q++ < for_end);
1839     }
1840     q = p;
1841     p = mem[p + 1].hh.v.RH;
1842   } while (!(p == rover));
1843 lab32:;
1844   p = mem_min;
1845   while (p <= lo_mem_max) {
1846     if ((mem[p].hh.v.RH == empty_flag)) 
1847     {
1848       print_nl("Bad flag at ");
1849       print_int(p);
1850     }
1851     while ((p <= lo_mem_max) && !freearr[p]) incr(p);
1852     while ((p <= lo_mem_max) && freearr[p]) incr(p);
1853   }
1854   if (printlocs)
1855   {
1856     print_nl("New busy locs:");
1857     {
1858       register integer for_end;
1859       p = mem_min;
1860       for_end = lo_mem_max;
1861       if (p <= for_end) do
1862         if (!freearr[p] && ((p > was_lo_max) || wasfree[p]))
1863         {
1864           print_char(' ');
1865           print_int(p);
1866         } while (p++ < for_end);
1867     }
1868     {
1869       register integer for_end;
1870       p = hi_mem_min;
1871       for_end = mem_end;
1872       if (p <= for_end) do
1873         if (!freearr[p] && ((p < was_hi_min) || (p > was_mem_end) || wasfree[p]))
1874         {
1875           print_char(' ');
1876           print_int(p);
1877         } while (p++ < for_end);
1878     }
1879   } 
1880   {
1881     register integer for_end;
1882     p = mem_min;
1883     for_end = lo_mem_max;
1884     if (p <= for_end) do
1885       wasfree[p]= freearr[p];
1886     while (p++ < for_end);
1887   }
1888   {
1889     register integer for_end;
1890     p = hi_mem_min;
1891     for_end = mem_end;
1892     if (p <= for_end) do
1893       wasfree[p] = freearr[p];
1894     while (p++ < for_end);
1895   }
1896   was_mem_end = mem_end;
1897   was_lo_max = lo_mem_max;
1898   was_hi_min = hi_mem_min;
1899 }
1900 #endif /* DEBUG */
1901
1902 #ifdef DEBUG
1903 void search_mem_(halfword p)
1904 {
1905   integer q; 
1906   {
1907     register integer for_end;
1908     q = mem_min;
1909     for_end = lo_mem_max;
1910     if (q <= for_end) do
1911     {
1912       if (link(q) == p)
1913       {
1914         print_nl("LINK(");
1915         print_int(q);
1916         print_char(')');
1917       }
1918       if (info(q) == p)
1919       {
1920         print_nl("INFO(");
1921         print_int(q);
1922         print_char(')');
1923       }
1924     } while (q++ < for_end);
1925   }
1926   {
1927     register integer for_end;
1928     q = hi_mem_min;
1929     for_end = mem_end;
1930     if (q <= for_end) do
1931     {
1932       if (link(q) == p)
1933       {
1934         print_nl("LINK(");
1935         print_int(q);
1936         print_char(')');
1937       }
1938       if (info(q) == p)
1939       {
1940         print_nl("INFO(");
1941         print_int(q);
1942         print_char(')');
1943       }
1944     } while (q++ < for_end);
1945   }
1946   {
1947     register integer for_end;
1948     q = 1;
1949     for_end = (hash_size + 1833);
1950     if (q <= for_end) do
1951     {
1952       if (eqtb[q].hh.v.RH == p)
1953       {
1954         print_nl("EQUIV(");
1955         print_int(q);
1956         print_char(')');
1957       }
1958     } while(q++ < for_end);
1959   }
1960   if (save_ptr > 0)
1961   {
1962     register integer for_end;
1963     q = 0;
1964     for_end = save_ptr - 1;
1965     if (q <= for_end) do 
1966     {
1967       if (save_stack[q].hh.v.RH == p)
1968       {
1969         print_nl("SAVE(");
1970         print_int(q);
1971         print_char(41);
1972       }
1973     } while (q++ < for_end);
1974   }
1975 /*  {register integer for_end; q = 0; for_end = 607; if (q <= for_end) do */
1976   {
1977     register integer for_end;
1978     q = 0;
1979     for_end = hyphen_prime;
1980     if (q <= for_end) do 
1981     {
1982       if (hyph_list[q]== p)
1983       {
1984         print_nl("HYPH(");
1985         print_int(q);
1986         print_char(')');
1987       }
1988     } while(q++ < for_end);
1989   }
1990 }
1991 #endif /* DEBUG */
1992
1993 void short_display_(integer p)
1994 {
1995   integer n; 
1996 /*  while(p > mem_min){ */
1997   while (p != 0) {      /* want p != null here bkph 93/Dec/15 !!! */
1998                 /* NOTE: still not fixed in 3.14159 ! */
1999      if ((p >= hi_mem_min))  /* is_char_node(p) */
2000      {
2001        if (p <= mem_end)
2002        {
2003          if (mem[p].hh.b0 != font_in_short_display) /* font(p) */
2004          {
2005            if ((mem[p].hh.b0 > font_max)) 
2006              print_char('*');
2007 /*    else print_esc(hash[(hash_size + 524) + mem[p].hh.b0].v.RH); */
2008            else //print_esc(hash[(hash_size + hash_extra + 524) + mem[p].hh.b0].v.RH);
2009            {print_esc("");print(hash[(hash_size + hash_extra + 524) + mem[p].hh.b0].v.RH);}
2010 /* 96/Jan/10 */
2011            print_char(' ');
2012            font_in_short_display = mem[p].hh.b0;
2013          }
2014          print(mem[p].hh.b1);          /* character(p) */
2015        }
2016     } else switch (mem[p].hh.b0)
2017     {
2018       case 0:
2019       case 1:
2020       case 3:
2021       case 8:
2022       case 4:
2023       case 5:
2024       case 13:
2025         print_string("[]");
2026         break;
2027       case 2:
2028         print_char('|');
2029         break;
2030       case 10:
2031         if (mem[p + 1].hh.v.LH != 0)
2032           print_char(' ');
2033         break;
2034       case 9:
2035         print_char('$');
2036         break;
2037       case 6:
2038         short_display(mem[p + 1].hh.v.RH);
2039         break;
2040       case 7:
2041         {
2042           short_display(mem[p + 1].hh.v.LH);
2043           short_display(mem[p + 1].hh.v.RH);
2044           n = mem[p].hh.b1;
2045           while (n > 0) {
2046             if (link(p) != 0) /* if link(p)<>null then */
2047               p = mem[p].hh.v.RH;
2048             decr(n);
2049           }
2050         }
2051         break;
2052       default:
2053         ;
2054         break;
2055     }
2056     p = mem[p].hh.v.RH;
2057   }
2058 }
2059
2060 void print_font_and_char_ (integer p)
2061 {
2062   if (p > mem_end)
2063     print_esc("CLOBBERED.");
2064   else {
2065     if ((mem[p].hh.b0 > font_max)) /* font(p) */
2066       print_char(42);   /* * */
2067 /*    else print_esc(hash[(hash_size + 524) + mem[p].hh.b0].v.RH); */
2068     else
2069       //print_esc(hash[(hash_size + hash_extra + 524) + mem[p].hh.b0].v.RH); /* 96/Jan/10 */
2070       {print_esc("");print(hash[(hash_size + hash_extra + 524) + mem[p].hh.b0].v.RH);}
2071     print_char(' ');
2072     print(mem[p].hh.b1);      /* character(p) */
2073   } 
2074
2075
2076 void print_mark_ (integer p)
2077
2078   print_char('{');
2079   if ((p < hi_mem_min)||(p > mem_end))
2080     print_esc("CLOBBERED.");
2081   else
2082     show_token_list(mem[p].hh.v.RH, 0, max_print_line - 10);
2083   print_char('}');
2084
2085
2086 void print_rule_dimen_ (scaled d)
2087 {
2088   if ((d == -1073741824L)) /* - 2^30 */
2089     print_char('*');
2090   else
2091     print_scaled(d);
2092 }
2093
2094 void print_glue_(scaled d, integer order, str_number s)
2095 {
2096   print_scaled(d); 
2097   if ((order < 0)||(order > 3))
2098     print_string("foul");
2099   else if (order > 0)
2100   {
2101     print_string("fil");
2102     while (order > 1) {
2103       print_char('l');
2104       decr(order);
2105     }
2106   } else if (s != 0)
2107     print(s);
2108 }
2109
2110 void print_spec_(integer p, str_number s)
2111 {
2112   if ((p < mem_min)||(p >= lo_mem_max)) 
2113     print_char('*');
2114   else {
2115     print_scaled(mem[p + 1].cint);
2116     if (s != 0)
2117       print(s);
2118     if (mem[p + 2].cint != 0)
2119     {
2120       print_string("plus");
2121       print_glue(mem[p + 2].cint, mem[p].hh.b0, s);
2122     }
2123     if (mem[p + 3].cint != 0)
2124     {
2125       print_string("minus");
2126       print_glue(mem[p + 3].cint, mem[p].hh.b1, s);
2127     }
2128   }
2129 }
2130
2131 void print_fam_and_char_(halfword p)
2132 {
2133   print_esc("fam");
2134   print_int(mem[p].hh.b0);
2135   print_char(' ');
2136   print(mem[p].hh.b1);
2137 }
2138
2139 void print_delimiter_(halfword p)
2140 {
2141   integer a;
2142   a = mem[p].qqqq.b0 * 256 + mem[p].qqqq.b1;
2143   a = a * 4096 + mem[p].qqqq.b2 * 256 + mem[p].qqqq.b3;
2144   if (a < 0)
2145     print_int(a);
2146   else
2147     print_hex(a);
2148
2149
2150 void print_subsidiary_data_(halfword p, ASCII_code c)
2151 {
2152   if ((pool_ptr - str_start[str_ptr]) >= depth_threshold)
2153   {
2154     if (mem[p].hh.v.RH != 0)
2155       print_string("[]");
2156   } else {
2157     {
2158       str_pool[pool_ptr]= c;
2159       incr(pool_ptr);
2160     }
2161     temp_ptr = p;
2162     switch (mem[p].hh.v.RH)
2163     {
2164       case 1:
2165         {
2166           print_ln();
2167           print_current_string();
2168           print_fam_and_char(p);
2169         }
2170         break;
2171       case 2:
2172         show_info();
2173         break;
2174       case 3:
2175         if (mem[p].hh.v.LH == 0)
2176         {
2177           print_ln();
2178           print_current_string();
2179           print_string("{}");
2180         } else show_info();
2181         break;
2182       default:
2183         ;
2184         break;
2185     }
2186     decr(pool_ptr);
2187   }
2188 }
2189 /* sec 0694 */
2190 void print_style_(integer c)
2191 {
2192   switch (c / 2)
2193   {
2194     case 0:
2195       print_esc("displaystyle");
2196       break;
2197     case 1:
2198       print_esc("textstyle");
2199       break;
2200     case 2:
2201       print_esc("scriptstyle");
2202       break;
2203     case 3:
2204       print_esc("scriptscriptstyle");
2205       break;
2206     default:
2207       print_string("Unknown style!");
2208       break;
2209   }
2210 }
2211 /* sec 0225 */
2212 void print_skip_param_(integer n)
2213 {
2214   switch(n)
2215   {
2216     case line_skip_code:
2217       print_esc("lineskip");
2218       break;
2219     case baseline_skip_code:
2220       print_esc("baselineskip");
2221       break; 
2222     case par_skip_code:
2223       print_esc("parskip");
2224       break;
2225     case above_display_skip_code:
2226       print_esc("abovedisplayskip");
2227       break;
2228     case below_display_skip_code:
2229       print_esc("belowdisplayskip");
2230       break;
2231     case above_display_short_skip_code:
2232       print_esc("abovedisplayshortskip");
2233       break;
2234     case below_display_short_skip_code:
2235       print_esc("belowdisplayshortskip");
2236       break;
2237     case left_skip_code:
2238       print_esc("leftskip");
2239       break;
2240     case right_skip_code:
2241       print_esc("rightskip");
2242       break;
2243     case top_skip_code:
2244       print_esc("topskip");
2245       break;
2246     case split_top_skip_code:
2247       print_esc("splittopskip");
2248       break;
2249     case tab_skip_code:
2250       print_esc("tabskip");
2251       break;
2252     case space_skip_code:
2253       print_esc("spaceskip");
2254       break;
2255     case xspace_skip_code:
2256       print_esc("xspaceskip");
2257       break;
2258     case par_fill_skip_code:
2259       print_esc("parfillskip");
2260       break;
2261     case thin_mu_skip_code:
2262       print_esc("thinmuskip");
2263       break;
2264     case med_mu_skip_code:
2265       print_esc("medmuskip");
2266       break; 
2267     case thick_mu_skip_code:
2268       print_esc("thickmuskip");
2269       break;
2270     default:
2271       print_string("[unknown glue parameter!]");
2272       break; 
2273   } 
2274
2275
2276 void show_node_list_(integer p)
2277 {/* 10 */ 
2278   integer n; 
2279   real g; 
2280 /* begin if cur_length>depth_threshold then */
2281   if ((pool_ptr - str_start[str_ptr]) > depth_threshold)
2282   {
2283 /*    if (p > 0) */  /* was p>null !!! line 3662 in tex.web */
2284     if (p != 0)    /* fixed 94/Mar/23 BUG FIX */
2285             /* NOTE: still not fixed in 3.14159 ! */
2286     print_string("[]");
2287     return; 
2288   } 
2289   n = 0; 
2290 /*  while(p > mem_min){ */  /* was p>mem_min !!! line 3667 in tex.web */
2291   while(p != 0){      /* want p != null - bkph 93/Dec/15 */
2292                 /* NOTE: still not fixed in 3.14159 ! */
2293     print_ln(); 
2294     print_current_string(); 
2295     if (p > mem_end)
2296     {
2297       print_string("Bad link, display aborted.");
2298       return;
2299     }
2300     incr(n);
2301     if (n > breadth_max)
2302     {
2303       print_string("etc.");
2304       return;
2305     }
2306     if ((p >= hi_mem_min))
2307       print_font_and_char(p);
2308     else switch (mem[p].hh.b0)
2309     {
2310       case 0:
2311       case 1:
2312       case 13:
2313         {
2314           if (mem[p].hh.b0 == 0)
2315             print_esc("h");
2316           else if (mem[p].hh.b0 == 1)
2317             print_esc("v");
2318           else print_esc("unset");
2319           print_string("box(");
2320           print_scaled(mem[p + 3].cint);
2321           print_char('+');
2322           print_scaled(mem[p + 2].cint);
2323           print_string(", shifted ");
2324           print_scaled(mem[p + 1].cint);
2325           if (mem[p].hh.b0 == 13)
2326           {
2327             if (mem[p].hh.b1 != 0)
2328             {
2329               print_string(" (");
2330               print_int(mem[p].hh.b1 + 1);
2331               print_string(" columns)");
2332             }
2333             if (mem[p + 6].cint != 0)
2334             {
2335               print_string(", stretch");
2336               print_glue(mem[p + 6].cint, mem[p + 5].hh.b1, 0);
2337             }
2338             if (mem[p + 4].cint != 0)
2339             {
2340               print_string(", shrink");
2341               print_glue(mem[p + 4].cint, mem[p + 5].hh.b0, 0);
2342             }
2343           } else {
2344             g = mem[p + 6].gr;
2345             if ((g != 0.0)&&(mem[p + 5].hh.b0 != 0))
2346             {
2347               print_string(", glue set");
2348               if (mem[p + 5].hh.b0 == 2)
2349                 print_string("- ");
2350               if (fabs(g)> 20000.0)
2351               {
2352                 if (g > 0.0)
2353                   print_char('>');
2354                 else
2355                   print_string("< -");
2356                 print_glue(20000 * 65536L, mem[p + 5].hh.b1, 0);
2357               } else print_glue(round(65536L * g), mem[p + 5].hh.b1, 0);
2358             }
2359             if (mem[p + 4].cint != 0)
2360             {
2361               print_string("shifted");
2362               print_scaled(mem[p + 4].cint);
2363             }
2364           }
2365           {
2366             {
2367               str_pool[pool_ptr]= 46;
2368               incr(pool_ptr);
2369             }
2370             show_node_list(mem[p + 5].hh.v.RH);
2371             decr(pool_ptr);
2372           }
2373         }
2374         break;
2375       case 2:
2376         {
2377           print_esc("rule(");
2378           print_rule_dimen(mem[p + 3].cint);
2379           print_char('+');
2380           print_rule_dimen(mem[p + 2].cint);
2381           print_string(")x");
2382           print_rule_dimen(mem[p + 1].cint);
2383         }
2384         break;
2385       case 3:
2386         {
2387           print_esc("insert");
2388           print_int(mem[p].hh.b1);
2389           print_string(",natural size ");
2390           print_scaled(mem[p + 3].cint);
2391           print_string("; split(");
2392           print_spec(mem[p + 4].hh.v.RH, 0);
2393           print_char(',');
2394           print_scaled(mem[p + 2].cint);
2395           print_string("(; float cost");
2396           print_int(mem[p + 1].cint);
2397           {
2398             {
2399               str_pool[pool_ptr]= 46;
2400               incr(pool_ptr);
2401             }
2402             show_node_list(mem[p + 4].hh.v.LH);
2403             decr(pool_ptr);
2404           }
2405         }
2406         break;
2407       case 8:
2408         switch (mem[p].hh.b1)
2409         {
2410           case 0:
2411             {
2412               print_write_whatsit(1279, p);   /* debug # (-1 to exit): */
2413               print_char('=');
2414               print_file_name(mem[p + 1].hh.v.RH, mem[p + 2].hh.v.LH, mem[p + 2].hh.v.RH);
2415             }
2416             break;
2417           case 1:
2418             {
2419               print_write_whatsit(591, p);  /* write */
2420               print_mark(mem[p + 1].hh.v.RH);
2421             }
2422             break;
2423           case 2:
2424             print_write_whatsit(1280, p); /* closeout */
2425             break;
2426           case 3:
2427             {
2428               print_esc("special");
2429               print_mark(mem[p + 1].hh.v.RH);
2430             }
2431             break;
2432           case 4:
2433             {
2434               print_esc("setlanguage");
2435               print_int(mem[p + 1].hh.v.RH);
2436               print_string(" (hyphenmin");
2437               print_int(mem[p + 1].hh.b0);
2438               print_char(',');
2439               print_int(mem[p + 1].hh.b1);
2440               print_char(')');
2441             }
2442             break;
2443           default:
2444             print_string("whatsit");
2445             break;
2446         }
2447         break;
2448       case 10:
2449         if (mem[p].hh.b1 >= 100)
2450         {
2451           print_esc("");
2452           if (mem[p].hh.b1 == 101)
2453             print_char('c');
2454           else if (mem[p].hh.b1 == 102)
2455             print_char('x');
2456           print_string("leaders ");
2457           print_spec(mem[p + 1].hh.v.LH, 0);
2458           {
2459             {
2460               str_pool[pool_ptr]= 46;
2461               incr(pool_ptr);
2462             }
2463             show_node_list(mem[p + 1].hh.v.RH);
2464             decr(pool_ptr);
2465           }
2466         } else {
2467           print_esc("glue");
2468           if (mem[p].hh.b1 != 0)
2469           {
2470             print_char('(');
2471             if (mem[p].hh.b1 < 98)
2472               print_skip_param(mem[p].hh.b1 - 1);
2473             else if (mem[p].hh.b1 == 98)
2474               print_esc("nonscript");
2475             else print_esc("mskip");
2476             print_char(')');
2477           }
2478           if (mem[p].hh.b1 != 98)
2479           {
2480             print_char(' ');
2481             if (mem[p].hh.b1 < 98)
2482               print_spec(mem[p + 1].hh.v.LH, 0);
2483             else
2484               print_spec(mem[p + 1].hh.v.LH, 334); /* mu */
2485           }
2486         }
2487         break;
2488       case 11:
2489         if (mem[p].hh.b1 != 99)
2490         {
2491           print_esc("kern");
2492           if (mem[p].hh.b1 != 0)
2493             print_char(' ');
2494           print_scaled(mem[p + 1].cint);
2495           if (mem[p].hh.b1 == 2)
2496             print_string(" (for accent)");
2497         } else {
2498           print_esc("mkern");
2499           print_scaled(mem[p + 1].cint);
2500           print_string("mu");
2501         }
2502         break;
2503       case 9:
2504         {
2505           print_esc("math");
2506           if (mem[p].hh.b1 == 0)
2507             print_string("on");
2508           else print_string("off");
2509           if (mem[p + 1].cint != 0)
2510           {
2511             print_string(", surrounded");
2512             print_scaled(mem[p + 1].cint);
2513           }
2514         }
2515         break;
2516       case 6:
2517         {
2518           print_font_and_char(p + 1);
2519           print_string("(ligature");
2520           if (mem[p].hh.b1 > 1)
2521             print_char('|');
2522           font_in_short_display = mem[p + 1].hh.b0; 
2523           short_display(mem[p + 1].hh.v.RH);
2524           if (odd(mem[p].hh.b1))
2525             print_char('|');
2526           print_char(')');
2527         }
2528         break;
2529       case 12:
2530         {
2531           print_esc("penalty ");
2532           print_int(mem[p + 1].cint);
2533         }
2534         break;
2535       case 7:
2536         {
2537           print_esc("discretionary");
2538           if (mem[p].hh.b1 > 0)
2539           {
2540             print_string(" replacing ");
2541             print_int(mem[p].hh.b1);
2542           }
2543           {
2544             {
2545               str_pool[pool_ptr]= 46;
2546               incr(pool_ptr);
2547             }
2548             show_node_list(mem[p + 1].hh.v.LH);
2549             decr(pool_ptr);
2550           }
2551           {
2552             str_pool[pool_ptr]= 124;
2553             incr(pool_ptr);
2554           }
2555           show_node_list(mem[p + 1].hh.v.RH);
2556           decr(pool_ptr);
2557         }
2558         break;
2559       case 4:
2560         {
2561           print_esc("mark");
2562           print_mark(mem[p + 1].cint);
2563         }
2564         break;
2565       case 5:
2566         {
2567           print_esc("vadjust");
2568           {
2569             {
2570               str_pool[pool_ptr]= 46;
2571               incr(pool_ptr);
2572             }
2573             show_node_list(mem[p + 1].cint);
2574             decr(pool_ptr);
2575           }
2576         }
2577         break;
2578       case 14:
2579         print_style(mem[p].hh.b1);
2580         break;
2581       case 15:
2582         {
2583           print_esc("mathchoice");
2584           {
2585             str_pool[pool_ptr]= 68;
2586             incr(pool_ptr);
2587           }
2588           show_node_list(mem[p + 1].hh.v.LH);
2589           decr(pool_ptr);
2590           {
2591             str_pool[pool_ptr]= 84;
2592             incr(pool_ptr);
2593           }
2594           show_node_list(mem[p + 1].hh.v.RH);
2595           decr(pool_ptr);
2596           {
2597             str_pool[pool_ptr]= 83;
2598             incr(pool_ptr);
2599           }
2600           show_node_list(mem[p + 2].hh.v.LH);
2601           decr(pool_ptr);
2602           {
2603             str_pool[pool_ptr]= 115;
2604             incr(pool_ptr);
2605           } 
2606           show_node_list(mem[p + 2].hh.v.RH); 
2607           decr(pool_ptr); 
2608         } 
2609         break;
2610       case 16:
2611       case 17:
2612       case 18:
2613       case 19:
2614       case 20:
2615       case 21:
2616       case 22:
2617       case 23:
2618       case 24:
2619       case 27:
2620       case 26:
2621       case 29:
2622       case 28:
2623       case 30:
2624       case 31:
2625         {
2626           switch (mem[p].hh.b0)
2627           {
2628             case 16:
2629               print_esc("mathord");
2630               break;
2631             case 17:
2632               print_esc("mathop");
2633               break;
2634             case 18:
2635               print_esc("mathbin");
2636               break;
2637             case 19:
2638               print_esc("mathrel");
2639               break;
2640             case 20:
2641               print_esc("mathopen");
2642               break;
2643             case 21:
2644               print_esc("mathclose");
2645               break;
2646             case 22:
2647               print_esc("mathpunct");
2648               break;
2649             case 23:
2650               print_esc("mathinner");
2651               break;
2652             case 27:
2653               print_esc("overline");
2654               break;
2655             case 26:
2656               print_esc("underline");
2657               break;
2658             case 29:
2659               print_esc("vcenter");
2660               break;
2661             case 24:
2662               {
2663                 print_esc("radical");
2664                 print_delimiter(p + 4);
2665               }
2666               break;
2667             case 28:
2668               {
2669                 print_esc("accent");
2670                 print_fam_and_char(p + 4);
2671               }
2672               break;
2673             case 30:
2674               {
2675                 print_esc("left");
2676                 print_delimiter(p + 1);
2677               }
2678               break;
2679             case 31:
2680               {
2681                 print_esc("right");
2682                 print_delimiter(p + 1);
2683               }
2684               break;
2685           } 
2686           if (mem[p].hh.b1 != 0)
2687             if (mem[p].hh.b1 == 1)
2688               print_esc("limits");
2689             else print_esc("nolimits");
2690           if (mem[p].hh.b0 < 30)
2691             print_subsidiary_data(p + 1, 46);
2692           print_subsidiary_data(p + 2, 94);
2693           print_subsidiary_data(p + 3, 95);
2694         }
2695         break;
2696       case 25:
2697         {
2698           print_esc("fraction");
2699           if (mem[p + 1].cint == 1073741824L)  /* 2^30 */
2700             print_string("= default");
2701           else print_scaled(mem[p + 1].cint); 
2702           if ((mem[p + 4].qqqq.b0 != 0) || (mem[p + 4].qqqq.b1 != 0) ||
2703               (mem[p + 4].qqqq.b2 != 0) || (mem[p + 4].qqqq.b3 != 0))
2704           {
2705             print_string(", left");
2706             print_delimiter(p + 4);
2707           }
2708           if ((mem[p + 5].qqqq.b0 != 0) || (mem[p + 5].qqqq.b1 != 0) ||
2709               (mem[p + 5].qqqq.b2 != 0)||(mem[p + 5].qqqq.b3 != 0))
2710           {
2711             print_string(", right");
2712             print_delimiter(p + 5);
2713           }
2714           print_subsidiary_data(p + 2, 92);
2715           print_subsidiary_data(p + 3, 47);
2716         }
2717         break;
2718       default:
2719         print_string("Unknown node type!");
2720         break;
2721     }
2722     p = mem[p].hh.v.RH;
2723   } 
2724
2725 /* NOTE: 262143L should be empty_flag */