|
DataMuseum.dkPresents historical artifacts from the history of: DKUUG/EUUG Conference tapes |
This is an automatic "excavation" of a thematic subset of
See our Wiki for more about DKUUG/EUUG Conference tapes Excavated with: AutoArchaeologist - Free & Open Source Software. |
top - metrics - downloadIndex: T d
Length: 11673 (0x2d99) Types: TextFile Names: »dviloop.c«
└─⟦52210d11f⟧ Bits:30007239 EUUGD2: TeX 3 1992-12 └─⟦af5ba6c8e⟧ »unix3.0/DVIWARE.tar.Z« └─⟦ca79c7339⟧ └─⟦this⟧ »DVIware/laser-setters/dvi-to-ps/TeXPS/dvitps/src/dviloop.c«
/* Copyright 1988 Stephan v. Bechtolsheim */ /* This file is part of the TeXPS Software Package. The TeXPS Software Package is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY. No author or distributor accepts responsibility to anyone for the consequences of using it or for whether it serves any particular purpose or works at all, unless he says so in writing. Refer to the TeXPS Software Package General Public License for full details. Everyone is granted permission to copy, modify and redistribute the TeXPS Software Package, but only under the conditions described in the TeXPS Software Package General Public License. A copy of this license is supposed to have been given to you along with TeXPS Software Package so you can know your rights and responsibilities. It should be in a file named CopyrightLong. Among other things, the copyright notice and this notice must be preserved on all copies. */ #include <stdio.h> #if SYS_V == 1 #include <string.h> #else #include <strings.h> #endif #include "defs.h" #include "units.h" #include "dvitps.h" #include "extfil.h" #include "fontd.h" #include "emit.h" #include "dvi-com.h" extern char *HandleFileNameExtension(); extern int Argc; extern char *Argv[1]; extern int Verbose; extern int ResetOption; extern int ResetPageNum; extern int OrderOfOutput; extern int ConformingDocument; extern int StderrOutputPageNumber; extern int StderrOutputPageNumberMod; extern EX_FILES Ex_PsOutput; extern void ResetBetweenPages(); extern void ReadDviPreAmble(); extern void ComputeConversionFactors(); extern void InitFontSubstitutionBusiness(); extern void PsBeginningSend(); extern void ReadDviPostAmble(); extern void PsMatrixSend(); extern int Pass1(); void HandleDviFileOpening(); void HandleDviFileClosing(); void LoopThroughDviFiles(); void ConformingDviFiles(); void NonConformingDviFiles(); void OpenNextDviFile(); int DviFileCounter; /* Number of dvi files handled by this driver */ EX_FILES ExDvi; /* File pointer, current .dvi file. */ /* Page Pointers. */ int FirstPP; /* Offset in dvi file: first page. */ int LastPP; /* Offset in dvi file: last page. */ int PrevPP; /* Offset in dvi file: previous page pointer. */ int Count[10]; /* \count0 .. 9 in dvi file. */ int CountPages; /* Usual orientation of pages in this document. */ int UsualOrientation = PORTRAIT_MODE; /* The orientation of the current page in particular. */ int ThisPagesOrientation = PORTRAIT_MODE; /* * LoopThroughDviFiles * ******************* * This routine is called by main() to start the processing of all * dvi files. There are two different ways of handling dvi files and * they are dealt with here. * * ret_decode_args: index where dvi file names start in Argv[..]. */ void LoopThroughDviFiles(ret_decode_args) int ret_decode_args; { if (ConformingDocument) ConformingDviFiles(ret_decode_args); /* -C option of driver */ else NonConformingDviFiles(ret_decode_args); /* Default. */ if (Verbose > V_QUIET && StderrOutputPageNumber != 0) fprintf (stderr, "\n"); } /* * NonConformingDviFiles * ********************* * The output by this driver generates by default non-conforming PostScript * output. The following procedure handles this case. * * ret_decode_args: index where dvi file names start in Argv[..]. * (passed down from LoopThroughDviFiles()) */ void NonConformingDviFiles(ret_decode_args) int ret_decode_args; { int dvi_i; /* Index dvi files. */ int ret_pass0; /* Return value of pass 0. */ int ret_pass1; /* Return value of pass 1. */ int potential_for_vm_reset; /* Is there potential for a VM reset? */ int command; /* Command from the dvi file. */ int done; /* Loop through all dvi files. */ for (dvi_i=ret_decode_args; dvi_i<Argc; dvi_i++) { OpenNextDviFile(0, dvi_i); /* Loop through the pages of a dvi file. Pass0() repositions dvi file, where it started out if so requested (argument is TRUE). Pass1() returns false iff it found the POST command. */ done = FALSE; while (!done) { CountPages++; /* Pass 0 is executed here. */ ret_pass0 = Pass0(TRUE); /* Evaluate result of Pass 0. */ switch (ret_pass0) { case PASS0_EOP_FOUND: break; case PASS0_POSTAMBLE_FOUND: break; default: Fatal2 ("NonConformingDviFiles(): illegal return code pass0: %d", ret_pass0); } /* If the orientation changed, a new matrix must be sent. */ if (UsualOrientation != ThisPagesOrientation) PsMatrixSend(); /* Pass1 is executed here. */ ret_pass1 = Pass1(); if (ret_pass0 == PASS0_POSTAMBLE_FOUND && ret_pass1 != PASS1_POSTAMBLE_FOUND) Fatal ("NonConformingDocument(): inconsistency A."); if (ret_pass0 != PASS0_POSTAMBLE_FOUND && ret_pass1 == PASS1_POSTAMBLE_FOUND) Fatal ("NonConformingDocument(): inconsistency B."); /* Orientation back to what it is normally in all cases. */ if (UsualOrientation != ThisPagesOrientation) { ThisPagesOrientation = UsualOrientation; PsMatrixSend(); } /* Proceed to the next page of the dvi file which may be the following page or the preceding page. */ switch (OrderOfOutput) { case ORDER_OUTPUT_FORWARD: /* No reason to reposition dvi file (correct from pass1). Done if Postamble read last. */ done = (ret_pass0 == PASS0_POSTAMBLE_FOUND); break; case ORDER_OUTPUT_REVERSE: if (PrevPP == -1) done = TRUE; else FExSeek (&ExDvi, PrevPP, FSEEK_ABS); break; default: Fatal ("NonConformingDocument(): OrderOfOutput"); } /* * A reset between pages can be triggered as follows: * (1) -z option when driver is invoked. * * The following is ugly code, but it works and it fixes * an extra prologue file which was appended to the end of * some of the PostScript files generated by this program. */ /* Is there potential for a VM reset? If not, just go on. */ if (ResetOption && !done && CountPages%ResetPageNum == 0) { /* Yes, it's worth looking. */ switch (OrderOfOutput) { case ORDER_OUTPUT_FORWARD: /* Read in the next command from the dvi file. We are interested in finding out whether it's a DVI_POST or a DVI_BOP command. If it's a DVI_BOP command, then more pages are in the dvi file and we will do a VM reset. If it's a DVI_POST, the postamble is coming and nothing else needs to be done. */ command = NoSignExtend(EX_FP(ExDvi), 1); FExSeek (&ExDvi, -1, FSEEK_REL); /* Position back. */ switch (command) { case DVI_BOP: ResetBetweenPages(); break; case DVI_POST: break; default: Fatal2 ("NonConformingDviFiles(): dvi: '%o illegal.", command); } break; /* In the case of reverse output, the done variable already reflects the fact, that there is no sense in an additional reset (that is done is already TRUE). So the program should never come here when the end of the dvi file is already reached (better, when the beginning of the dvi fils is already reached, because we are talking about reverse output here. */ case ORDER_OUTPUT_REVERSE: ResetBetweenPages(); break; } } } /* While loop pages of dvi file */ FExClose (&ExDvi); } /* End of loop of all dvi file pages. */ } /* * ConformingDviFiles * ****************** * Generate a "conforming PostScript output" type of output. In that * case we first have to do all pass0s of all .dvi files, and then * all pass1s. * * ret_decode_args: index where dvi file names start in Argv[..]. * (passed down from LoopThroughDviFiles()) */ void ConformingDviFiles(ret_decode_args) int ret_decode_args; { int dvi_i; /* Index dvi files. */ int ret_pass0; /* return pass 0 */ int ret_pass1; /* return pass 1 */ int done; int n; /* Pass0 of all the dvi files. */ for (dvi_i=ret_decode_args; dvi_i<Argc; dvi_i++) { OpenNextDviFile(1, dvi_i); done = FALSE; while (! done) { CountPages++; ret_pass0 = Pass0(FALSE); switch (ret_pass0) { case PASS0_EOP_FOUND: break; case PASS0_POSTAMBLE_FOUND: done = TRUE; break; default: Fatal2 ("ConformingDviFiles(): illegal return code pass0: %d", ret_pass0); } /* Proceed to the next page of the dvi file which may be the following page or the preceding page. */ switch (OrderOfOutput) { case ORDER_OUTPUT_FORWARD: /* No reason to reposition dvi file. */ break; case ORDER_OUTPUT_REVERSE: if (PrevPP == -1) done = TRUE; else FExSeek (&ExDvi, PrevPP, FSEEK_ABS); break; default: Fatal ("ConformingDviFiles(): OrderOfOutput-2"); } } /* while (!done) */ FExClose (&ExDvi); if (StderrOutputPageNumber != 0) { fprintf (stderr, "\n"); StderrOutputPageNumber = 0; } } /* Pass0 for all dvi files. */ /* This is the end of the prologue as far as conforming documents are concerned. */ fprintf (EX_FP(Ex_PsOutput), "%%%%EndProlog\n"); /* Next round: Pass 1 of all dvi files. */ for (dvi_i=ret_decode_args; dvi_i<Argc; dvi_i++) { OpenNextDviFile(1, dvi_i); n = CountPages; CountPages = 0; done = FALSE; while (! done) { CountPages++; if (CountPages != n) fprintf (EX_FP(Ex_PsOutput), "%%%%Page: ? %d\n", CountPages); ret_pass1 = Pass1(); /* Position to the "next page" of the dvi file, which may be the following page or the preceding page. */ switch (OrderOfOutput) { case ORDER_OUTPUT_FORWARD: /* No reason to reposition dvi file. */ if (ret_pass1 == PASS1_POSTAMBLE_FOUND) done = TRUE; break; case ORDER_OUTPUT_REVERSE: if (PrevPP == -1) done = TRUE; else FExSeek (&ExDvi, PrevPP, FSEEK_ABS); break; default: Fatal ("ConformingDviFiles(): OrderOfOutput-3"); } /* switch */ } FExClose (&ExDvi); } /* Pass 1 for all dvi files */ } int StdinCludge = FALSE; /* Will be set to true after the first call to OpenNextDviFile, control == 1, and file name == "-" */ /* * OpenNextDviFile * *************** * Open the next dvi file. * control: 0: non-conforming document generated. * 1: conforming document generated so this routine will be called * twice. * index: index into Argv[.] for the file name. */ void OpenNextDviFile(control, index) int control; int index; { switch(control) { /* A nonconforming document is generated, so the .dvi file is read in only once. */ case 0: FExOpen (&ExDvi, EFT_READ, EFQ_STDIN_TMP_FILE, Argv[index], "dvi"); break; /* A conforming document is generated. */ case 1: if (Strcmp(Argv[index], "-") == 0) { if (StdinCludge) FExOpen (&ExDvi, EFT_READ, EFQ_STDIN_TWICE_SECOND_TIME, "-", NULL); else { StdinCludge = TRUE; FExOpen (&ExDvi, EFT_READ, EFQ_STDIN_TWICE, "-", NULL); } } else /* not stdin! */ FExOpen (&ExDvi, EFT_READ, 0, Argv[index], "dvi"); break; default: Fatal("OpenNextDviFile(): default."); } /* Read in preamble, compute factors, set up some font business. */ ReadDviPreAmble(); ComputeConversionFactors(); InitFontSubstitutionBusiness(); PsBeginningSend(); ReadDviPostAmble(); /* Position correctly within the .dvi file. */ switch (OrderOfOutput) { case ORDER_OUTPUT_FORWARD: FExSeek(&ExDvi, FirstPP, FSEEK_ABS); break; case ORDER_OUTPUT_REVERSE: FExSeek(&ExDvi, LastPP, FSEEK_ABS); break; } ThisPagesOrientation = UsualOrientation; }