4.4BSD/usr/src/contrib/dipress/src/bin/ipmetrics/ipmetrics.c

Compare this file to the similar file:
Show the results in this format:

/*
 *
 * Copyright (c) 1984, 1985, 1986 Xerox Corp.
 *
 * Owner: Lee Moore
 *
 * Description:
 *    This program reads an Interpress file, executes it and produces a
 *    set of Troff printer description files.  
 *
 *    The metrics file will be read from the file "name.ip",
 *    where name is read from the command line.  The ".ip"
 *    extension will not be added if it is already present in the
 *    name.
 *
 * HISTORY
 * 18-Aug-86  Lee Moore (lee) at Xerox Webster Research Center
 *	Moved typesetter specific routine calls to the file "conf.c".
 *
 * 15-Apr-86  Lee Moore (lee) at Xerox Webster Research Center
 *	Added table of contents mode (toc).
 *
 * 04-Feb-86  lee at Xerox, WRC
 *	Added the ability to execute several masters instead of just one.
 *
 * 06-Jan-86  Lee Moore(lee) at Xerox, WRC
 *	Converted for use with ipmetrics.
 */

#include <stdio.h>
#include <strings.h>
#include "stack.h"
#include "token.h"
#include "config.h"
#include "ipmetrics.h"
#include "conf.h"

#define TRUE	1
#define FALSE	0

#define SAME	0

extern struct CompositionSwitch CompositionSwitch[];

extern char *getstring();
extern char *malloc();

extern unsigned char **getvector();

struct FontConfig *ReadConfigFile();

char *LibraryDirectory = "../lib",
      LibraryDirStorage[1024];


#define err0 "ipmetrics: No input ip file name!\n"
#define err1 "ipmetrics: ip file could not be found, %s!\n"

FILE *fpin;
int fdout;
char DeviceName1[MAXTOKENSIZE];
char *DeviceName = DeviceName1;


main(argc, argv)
  int argc;
  char *argv[];
  {
	int system;
	struct FontConfig *configChain;
	unsigned char *fontVec;
  	struct CompositionSwitch *csp;
  
	DebugLevel = 0;
	system = getargs(argc, argv);

	csp = &CompositionSwitch[system];

	if( csp->cs_readConfigFile )
	  	configChain = ReadConfigFile();

	fprintf(stderr, "output initialization...\n");
	(* csp->cs_initializationProc)(configChain);

	/* call the metrics vector processing routine for each font vector */
	while (!stackempty()) {
   		fontVec = pop(0, 0);
		(* csp->cs_fontProc)(configChain, fontVec);
    		free((char *) fontVec); }   /* should do a recursive free? */

	fprintf(stderr, "cleaning-up...\n");
	(* csp->cs_cleanUpProc)(configChain);
	fprintf(stderr, "done.\n");
  	exit(0);
  }



/*
 * process the command line arguments
 */

getargs(argc, argv)
  int argc;
  char *argv[];
  {
  char *filename;
  extern int optind;
  extern char *optarg;
  int system,
	c;
  char systemName[30];
  struct CompositionSwitch *csp;

  (void) strcpy(systemName, "troff");

  while ((c = getopt(argc, argv, "c:d:")) != EOF)
	switch (c) {
	    case 'd':
		(void) strncpy(LibraryDirStorage, optarg, sizeof(LibraryDirStorage));
		LibraryDirectory = LibraryDirStorage;
		break;

	    case 'c':
		(void) strncpy(systemName, optarg, sizeof(systemName));
		break;

	    default:
		printf("ipmetrics: option '%c' not allowed\n");
	}

  /* look-up system name */
  for(csp = CompositionSwitch, system = 0; csp->cs_systemName != NULL; csp++, system++)
  	if( strncmp(csp->cs_systemName, systemName, sizeof(systemName)) == SAME)
	    break;

  if( csp->cs_systemName == NULL) {
	printf("unknown system: %s\n", systemName);
	exit(1); }

  if (argc == optind) {	/* at least one argument */
	error(err0);
	exit(1);
  }
  printf("executing...\n");

  for( ; optind < argc ; optind++ ) {
	/* Open input IP file. */
	fdout = 1;
	filename = (char *) malloc((unsigned) strlen(argv[optind])+1+strlen(".ip"));
	(void) strcpy(filename, argv[optind]);

	if (strcmp(".ip", rindex(filename, '.')) != 0)
		(void) strcat(filename, ".ip");

	fpin = fopen(filename, "r");

	if (fpin == NULL) {
		fprintf(stderr, err1, filename);
		exit(2);
	}

	printf("\t%s\n", filename); (void) fflush(stdout);
  	parse(fpin);
  }

  return system;
  }



/*
 * read the font configuration file
 */
struct FontConfig *
ReadConfigFile() {
	char token[MAXTOKENSIZE];
	struct TokenState *ts;
	struct FontConfig **last,
			   *p,
			   *configChain;

	printf("reading configuration file\n");
	last = &configChain;
	ts = InitTokenStream(stdin);
	GetToken(ts, token, MAXTOKENSIZE);

	if( strcmp(token, "device") != 0 ) {
		fprintf(stderr, "first token is %s, not 'device'\n", token);
		exit(1); }

	GetToken(ts, DeviceName, MAXTOKENSIZE);
	printf("\tdevice is %s\n", DeviceName);

	while( !EndOfFile(ts) ) {
		p = (struct FontConfig *)
			malloc((unsigned) sizeof(struct FontConfig));

		GetToken(ts, p->FontPt1, MAXTOKENSIZE);

		if( EndOfLine(ts) ) {
			fprintf(stderr,
				"lines ends prematurely; last token was `%s'\n",
				p->FontPt1);
			exit(2);}

		GetToken(ts, p->FontPt2, MAXTOKENSIZE);

		if( EndOfLine(ts) ) {
			fprintf(stderr,
				"lines ends prematurely; last token was `%s'\n",
				p->FontPt2);
			exit(2);}

		GetToken(ts, p->FontPt3, MAXTOKENSIZE);

		if( EndOfLine(ts) ) {
			fprintf(stderr,
				"lines ends prematurely; last token was `%s'\n",
				p->FontPt3);
			exit(2);}

		GetToken(ts, p->TargetName, MAXTOKENSIZE);

		if( !EndOfLine(ts) )
			GetToken(ts, p->MapFile, MAXTOKENSIZE);
		else
			p->MapFile[0] = '\0';

		p->Next = NULL;
		*last = p;
		last = &p->Next;
	}

	return configChain;
  }




/*
 * get the font name from a font vector
 */

GetFontNameProperty(fontDescVec, CName)
   unsigned char *fontDescVec;
   char *CName[3]; {
	unsigned char *nameProperty,
		     **nameVec;
	int i;

	if( (nameProperty = GetStringProp("name", fontDescVec)) == NULL ) {
		printf("ipmetrics: can't find 'name' property\n");
		return FALSE;
	}

	nameVec = getvector(nameProperty);

	/* loop for each part of the three part name */
	for( i = 0; i < 3; i++ ) {
		if( gettype(nameVec[i]) != type_string ) {
			printf("name vector not of type string\n");
			free((char *) nameVec);
			return FALSE;
		}

		if( getsubtype(nameVec[i]) != subtype_identifier ) {
			printf("name subtype not an identifier\n");
			free((char *) nameVec);
			return FALSE;
		}

		CName[i] = getstring(nameVec[i], subtype_identifier);
	}

	free((char *) nameVec);
	return TRUE;
   }


/*
 * get a property off the property-vector whose type is "string"
 */

unsigned char *
GetStringProp(propName, list)
     char *propName;
     unsigned char *list; {
	int i,
	    vecLength;
	char *candidate;
	unsigned char **listArray,
			*result;

	if( gettype(list) != type_vector ) {
		printf("ipmetric: non-vector found in stack!\n");
		return NULL;}

	if( getsubtype(list) != subtype_general ) {
		printf("ipmetric: vector sub-type is not 'general'\n");
		return NULL; }

	if( (vecLength = getdepth(list)) & 01 ) {
		printf("ipmetrics: property vector is of odd length\n");
		return NULL;}

	listArray = getvector(list);

	/* cdr down the list */
	for( i = 0; i < vecLength; i += 2 ) {
		if( ! checktype(listArray[i], type_string, subtype_identifier) ) {
			printf("ipmetrics: property of incorrect type\n");
			free((char *) listArray);
			return NULL;}

		candidate = getstring(listArray[i], subtype_identifier);

	        if( strcmp(propName, candidate) == 0 ) {
			result = listArray[i+1];
			free((char *) listArray);
			return result;
		}
	}

	free((char *) listArray);
	return NULL;
     }


/*
 * get a property from the property-vector that is type "integer"
 */

unsigned char *
GetIntegerProp(property, list)
     int property;
     unsigned char *list; {
	int i,
	    vecLength;
	int candidate;
	unsigned char **listArray,
			*result;

	if( gettype(list) != type_vector ) {
		printf("ipmetric: non-vector found in stack!\n");
		return NULL;}

	if( getsubtype(list) != subtype_general ) {
		printf("ipmetric: vector sub-type is not 'general'\n");
		return NULL; }

	if( (vecLength = getdepth(list)) & 01 ) {
		printf("ipmetrics: property vector is of odd length\n");
		return NULL;}

	listArray = getvector(list);

	for( i = 0; i < vecLength; i += 2 ) {
		if( ! checktype(listArray[i], type_number, subtype_integer) ) {
			printf("ipmetrics: property of incorrect type\n");
			free((char *) listArray);
			return NULL;}

		candidate = getint(listArray[i]);

	        if( property == candidate ) {
			result = listArray[i+1];
			free((char *) listArray);
			return result;
		}
	}

	free((char *) listArray);
	return NULL;
     }