1 /* Copyright 1992 Karl Berry
\r
2 Copyright 2007 TeX Users Group
\r
3 Copyright 2014 Clerk Ma
\r
5 This program is free software; you can redistribute it and/or modify
\r
6 it under the terms of the GNU General Public License as published by
\r
7 the Free Software Foundation; either version 2 of the License, or
\r
8 (at your option) any later version.
\r
10 This program is distributed in the hope that it will be useful, but
\r
11 WITHOUT ANY WARRANTY; without even the implied warranty of
\r
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
\r
13 General Public License for more details.
\r
15 You should have received a copy of the GNU General Public License
\r
16 along with this program; if not, write to the Free Software
\r
17 Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
\r
22 #include "yandytex.h"
\r
24 #define dump_ext_length 4
\r
25 #define edit_value tex_edit_value
\r
27 extern char * replacement[];
\r
35 int main (int ac, char *av[])
\r
37 int flag = 0, ret = 0;
\r
42 if (main_init(gargc, gargv))
\r
45 TEX_format_default = " plain.fmt";
\r
46 format_default_length = strlen(TEX_format_default + 1);
\r
50 ret = setjmp(jumpbuffer);
\r
54 flag = main_program();
\r
57 printf("EXITING at %s: flag = %d, ret = %d, jump_used = %d\n", "main", flag, ret, jump_used);
\r
62 printf("EXITING at %s: flag = %d, ret = %d, jump_used = %d\n", "jump_out", flag, ret, jump_used);
\r
65 if (endit(flag) != 0)
\r
66 flag = 1; /* do final clean up in local.c */
\r
74 /* texk/web2c/lib/texmfmp.c */
\r
75 void t_open_in (void)
\r
81 if (gargc > optind && optind > 0)
\r
83 for (i = optind; i < gargc; i++)
\r
85 if (allow_quoted_names && strchr(gargv[i], ' ') != NULL)
\r
87 (void) strcat ((char *) &buffer[first], "\"");
\r
88 (void) strcat ((char *) &buffer[first], gargv[i]);
\r
89 (void) strcat ((char *) &buffer[first], "\"");
\r
92 (void) strcat ((char *) &buffer[first], gargv[i]);
\r
94 (void) strcat ((char *) &buffer[first], " ");
\r
100 /* Find the end of the buffer. */
\r
101 for (last = first; buffer[last]; ++last)
\r
104 for (--last; last >= first && ISBLANK (buffer[last]) && buffer[last] != '\r'; --last)
\r
109 /* One more time, this time converting to TeX's internal character
\r
110 representation. */ /* for command line input in this case */
\r
113 for (i = first; i < last; i++)
\r
114 buffer[i] = xord[buffer[i]];
\r
118 static void catch_interrupt (int err)
\r
121 (void) signal(SIGINT, SIG_IGN);
\r
123 if (interrupt++ >= 3)
\r
126 (void) signal(SIGINT, catch_interrupt);
\r
129 void fix_date_and_time (void)
\r
134 (void) time(&clock);
\r
137 printf("The time is %lld\n", (long long)clock);
\r
140 puts("Time not available!");
\r
142 tmptr = localtime (&clock);
\r
146 printf("Cannot convert time (%0lld)!\n", (long long)clock);
\r
150 tex_time = 22 * 60 + 14;
\r
154 tex_time = tmptr->tm_hour * 60 + tmptr->tm_min;
\r
155 day = tmptr->tm_mday;
\r
156 month = tmptr->tm_mon + 1;
\r
157 year = tmptr->tm_year + 1900;
\r
160 printf("%d-%d-%d %d:%d\n",
\r
161 tmptr->tm_year + 1900,
\r
170 if (signal(SIGINT, catch_interrupt) == SIG_ERR)
\r
172 puts(" CTRL-C handler not installed");
\r
173 uexit(EXIT_FAILURE);
\r
176 void (*old_handler)();
\r
178 old_handler = signal(SIGINT, catch_interrupt);
\r
180 if (old_handler != SIG_DFL)
\r
181 (void) signal(SIGINT, old_handler);
\r
186 /* I/O for TeX and Metafont. */
\r
187 void complain_line (FILE * output)
\r
189 show_line("\n", 0);
\r
191 #ifdef ALLOCATEBUFFER
\r
192 sprintf(log_line, "! Unable to read an entire line---buf_size=%d.\n", current_buf_size);
\r
194 sprintf(log_line, "! Unable to read an entire line---buf_size=%d.\n", buf_size);
\r
197 fputs(log_line, output);
\r
198 puts(" (File may have a line termination problem.)");
\r
201 void show_bad_line (FILE * output, int first, int last)
\r
204 char *s = log_line;
\r
206 for (i = first; i <= last; i++)
\r
210 if (show_in_hex && (ch > 127))
\r
235 *s++ = (char) (ch + 64);
\r
237 else if (ch == 127)
\r
241 *s++ = (char) (ch - 64);
\r
252 fputs(log_line, output); // log_file
\r
255 boolean input_line_finish (void)
\r
260 buffer[last] = ' ';
\r
262 if (last >= max_buf_stack)
\r
263 max_buf_stack = last;
\r
265 while (last > first)
\r
267 i = buffer[last - 1];
\r
269 if (i == ' ' || i == '\t')
\r
275 if (restrict_to_ascii)
\r
279 for (i = first; i <= last; i++)
\r
283 if (ch > 126 || (ch < ' ' && ch != '\t' && ch != '\f' && ch != '\r' && ch != '\n'))
\r
285 sprintf(log_line, "\n! non ASCII char (%d) in line: ", ch);
\r
286 show_line(log_line, 1);
\r
289 fprintf(log_file, "\n! non ASCII char (%d) in line: ", ch);
\r
298 show_bad_line(errout, first, last);
\r
301 show_bad_line(log_file, first, last);
\r
307 for (i = first; i <= last; i++)
\r
308 buffer[i] = xord[buffer[i]];
\r
314 /* Read a line of input into buffer as efficiently as possible (ha ha)
\r
315 while still looking like Pascal.
\r
316 We set `last' to `first' and return `false' if we get to eof.
\r
317 Otherwise, we return `true' and set last = first +
\r
318 length(line except trailing whitespace). */
\r
320 boolean input_line (FILE * f)
\r
322 char * u; /* 1994/July/3 for key_replace */
\r
326 /* following is new version with tab expansion and key replacement */
\r
327 /* may want to expand out separately for speed 1994/July/3 */
\r
328 /* different versions depending on return_flag / tabexpand / key_replace */
\r
329 /* while (last < buf_size && (i = getc (f)) != EOF) */
\r
330 #ifdef ALLOCATEBUFFER
\r
333 while (last < buf_size)
\r
340 if (i == EOF || i == '\n' || (i == '\r' && return_flag))
\r
342 else if (i == '\t' && tab_step != 0)
\r
344 buffer[last++] = (ASCII_code) ' ';
\r
346 #ifdef ALLOCATEBUFFER
\r
347 if (last >= current_buf_size)
\r
349 buffer = realloc_buffer(increment_buf_size);
\r
351 if (last >= current_buf_size)
\r
356 #ifdef ALLOCATEBUFFER
\r
357 while ((last - first) % tab_step != 0)
\r
359 while (last < buf_size && (last - first) % tab_step != 0)
\r
363 buffer[last++] = (ASCII_code) ' ';
\r
365 #ifdef ALLOCATEBUFFER
\r
366 if (last >= current_buf_size)
\r
368 buffer = realloc_buffer(increment_buf_size);
\r
370 if (last >= current_buf_size)
\r
380 if (key_replace && (u = replacement[i]) != NULL)
\r
382 #ifdef ALLOCATEBUFFER
\r
383 while (*u != '\0')
\r
385 while (last < buf_size && *u != '\0')
\r
388 buffer[last++] = (ASCII_code) *u++;
\r
390 #ifdef ALLOCATEBUFFER
\r
391 if (last >= current_buf_size)
\r
393 buffer = realloc_buffer(increment_buf_size);
\r
395 if (last >= current_buf_size)
\r
401 else /* normal case */
\r
403 buffer[last++] = (ASCII_code) i;
\r
405 #ifdef ALLOCATEBUFFER
\r
406 if (last >= current_buf_size)
\r
408 buffer = realloc_buffer(increment_buf_size);
\r
410 if (last >= current_buf_size)
\r
417 if (return_flag) /* let return terminate line as well as newline */
\r
419 if (i == '\r') /* see whether return followed by newline */
\r
421 i = getc (f); /* in which case throw away the newline */
\r
428 /* else buffer[last-1] = (ASCII_code) i; */
\r
432 // Turn Ctrl-Z at end of file into newline 2000 June 22
\r
433 if (i == EOF && trimeof && buffer[last - 1] == 26)
\r
438 if (i == EOF && last == first)
\r
441 /* Didn't get the whole line because buffer was too small? */
\r
442 /* This shouldn't happen anymore 99/Jan/23 */
\r
443 if (i != EOF && i != '\n' && i != '\r')
\r
445 complain_line(errout);
\r
448 complain_line(log_file);
\r
450 /* This may no longer be needed ... now that we grow it */
\r
451 if (truncate_long_lines)
\r
453 while (i != EOF && i != '\n' && i != '\r')
\r
455 i = getc (f); // discard rest of line
\r
458 last--; /* just in case */
\r
461 uexit(EXIT_FAILURE); /* line too long */
\r
464 return input_line_finish();
\r
467 static char * edit_value = "c:\\yandy\\WinEdt\\WinEdt.exe [Open('%s');SelLine(%d,7)]";
\r
469 static inline int Isspace (char c)
\r
471 return (c == ' ' || c == '\t');
\r
474 void call_edit (ASCII_code * filename, pool_pointer fnstart, integer fnlength, integer linenumber)
\r
476 char *temp, *command, *fullcmd;
\r
478 int sdone, ddone, i;
\r
481 char *fp, *ffp, *env, editorname[256], buffer[256];
\r
483 int dontchange = 0;
\r
487 filename += fnstart;
\r
489 /* Close any open input files, since we're going to kill the job. */
\r
490 for (i = 1; i <= in_open; i++)
\r
492 xfclose (input_file[i]->f, "inputfile");
\r
494 xfclose (input_file[i], "inputfile");
\r
497 /* Replace the default with the value of the appropriate environment
\r
498 variable or config file value, if it's set. */
\r
499 temp = kpse_var_value("TEXEDIT");
\r
504 /* Construct the command string. The `11' is the maximum length an
\r
505 integer might be. */
\r
506 command = (char *) xmalloc (strlen (edit_value) + fnlength + 11);
\r
508 /* So we can construct it as we go. */
\r
513 if ((isalpha(*edit_value) && *(edit_value + 1) == ':'
\r
514 && IS_DIR_SEP (*(edit_value + 2)))
\r
515 || (*edit_value == '"' && isalpha(*(edit_value + 1))
\r
516 && *(edit_value + 2) == ':'
\r
517 && IS_DIR_SEP (*(edit_value + 3)))
\r
522 while ((c = *edit_value++) != 0)
\r
526 switch (c = *edit_value++)
\r
530 FATAL ("call_edit: `%%d' appears twice in editor command");
\r
531 sprintf (temp, "%ld", (long int)linenumber);
\r
532 while (*temp != '\0')
\r
539 FATAL ("call_edit: `%%s' appears twice in editor command");
\r
540 for (i = 0; i < fnlength; i++)
\r
541 *temp++ = xchr[(filename[i])];
\r
547 /* Back up to the null to force termination. */
\r
564 if(Isspace(c) && cnt == 0)
\r
571 else if(!Isspace(c) && cnt == 0)
\r
589 if (dontchange == 0) {
\r
590 if(editorname[0] == '.' ||
\r
591 editorname[0] == '/' ||
\r
592 editorname[0] == '\\') {
\r
593 fprintf(stderr, "%s is not allowed to execute.\n", editorname);
\r
596 env = (char *)getenv("PATH");
\r
597 if(SearchPath(env, editorname, ".exe", 256, buffer, &ffp)==0) {
\r
598 if(SearchPath(env, editorname, ".bat", 256, buffer, &ffp)==0) {
\r
599 fprintf(stderr, "I cannot find %s in the PATH.\n", editorname);
\r
603 fullcmd = (char *)xmalloc(strlen(buffer)+strlen(command)+5);
\r
604 strcpy(fullcmd, "\"");
\r
605 strcat(fullcmd, buffer);
\r
606 strcat(fullcmd, "\"");
\r
607 strcat(fullcmd, command);
\r
612 /* Execute the command. */
\r
613 if (system (fullcmd) != 0)
\r
614 fprintf(stderr, "! Trouble executing `%s'.\n", command);
\r
616 /* Quit, since we found an error. */
\r
621 #if !defined (WORDS_BIGENDIAN) && !defined (NO_FMTBASE_SWAP)
\r
623 /* We don't REALLY care what `endian' the machine is after all ! */
\r
626 // char swapmarkerstring="ERROR: SWAPPING - NOT BigEndian AND NOT NoFmtBaseSwap";
\r
629 /* This macro is always invoked as a statement. It assumes a variable
\r
632 #define SWAP(x, y) temp = (x); (x) = (y); (y) = temp;
\r
635 /* Make the NITEMS items pointed at by P, each of size SIZE, be the
\r
636 opposite-endianness of whatever they are now. */
\r
638 static int swap_items (char *p, int nitems, int size)
\r
642 /* Since `size' does not change, we can write a while loop for each
\r
643 case, and avoid testing `size' for each time. */
\r
675 /* Nothing to do. */
\r
679 show_line("\n", 0);
\r
680 sprintf(log_line, "! I can't (un)dump a %d byte item.\n", size);
\r
681 show_line(log_line, 1);
\r
682 uexit(EXIT_FAILURE);
\r
686 #endif /* not WORDS_BIGENDIAN and not NO_FMTBASE_SWAP */
\r
688 #ifdef COMPACTFORMAT
\r
689 int do_dump (char *p, int item_size, int nitems, gzFile out_file)
\r
691 int do_dump (char *p, int item_size, int nitems, FILE *out_file)
\r
694 #if !defined (WORDS_BIGENDIAN) && !defined (NO_FMTBASE_SWAP)
\r
695 swap_items (p, nitems, item_size);
\r
698 #ifdef COMPACTFORMAT
\r
699 if (gzwrite(out_file, p, (item_size * nitems)) != (item_size * nitems))
\r
701 if ((int) fwrite(p, item_size, nitems, out_file) != nitems)
\r
704 printf("\n! Could not write %d %d-byte item%s.\n",
\r
705 nitems, item_size, (nitems > 1) ? "s" : "");
\r
706 uexit(EXIT_FAILURE);
\r
709 /* Have to restore the old contents of memory, since some of it might get used again. */
\r
710 #if !defined (WORDS_BIGENDIAN) && !defined (NO_FMTBASE_SWAP)
\r
711 swap_items (p, nitems, item_size);
\r
717 #ifdef COMPACTFORMAT
\r
718 int do_undump (char *p, int item_size, int nitems, gzFile in_file)
\r
720 int do_undump (char *p, int item_size, int nitems, FILE *in_file)
\r
723 #ifdef COMPACTFORMAT
\r
724 if (gzread(in_file, (void *) p, (unsigned int) (item_size * nitems)) <= 0)
\r
726 if ((int) fread((void *) p, item_size, nitems, in_file) != nitems)
\r
729 printf("\n! Could not read %d %d-byte item%s.\n",
\r
730 nitems, item_size, (nitems > 1) ? "s" : "");
\r
731 uexit(EXIT_FAILURE);
\r
734 #if !defined (WORDS_BIGENDIAN) && !defined (NO_FMTBASE_SWAP)
\r
735 swap_items (p, nitems, item_size);
\r
741 #ifdef FUNNY_CORE_DUMP
\r
743 void funny_core_dump (void)
\r
748 switch (pid = vfork ())
\r
751 perrormod ("vfork");
\r
755 (void) signal (SIGQUIT, SIG_DFL);
\r
756 (void) kill (getpid (), SIGQUIT);
\r
757 (void) write (2, "how did we get here?\n", 21);
\r
761 while ((w = wait (&status)) != pid && w != -1)
\r
764 if (status.w_coredump)
\r
767 (void) write (2, "attempt to dump core failed\n", 28);
\r
771 #endif /* FUNNY_CORE_DUMP */