⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 maha.c

📁 早期freebsd实现
💻 C
📖 第 1 页 / 共 2 页
字号:
/* *  maharani - a czarina-like program that generates interpress files * *  Written for Xerox Corporation by William LeFebvre * *  Copyright (c)  1984, 1985, 1986 Xerox Corporation * *  HISTORY * 23-Sep-86  Lee Moore (lee) at Xerox Webster Research Center *	Added Jim Mayer's fix to the space allocator. * * 13-apr-86  Ed Flint (ed) at Xerox Webster Research Center *	do_file will reset to left margin when encountering carriage return * * 11-Feb-86  Lee Moore (lee) at Xerox Webster Research Center *	Added various suggestions from Larry Parmalee at Cornell U. *	1)  Margin adjustments.  Margins vary according to portrait or *	    landscape mode.  If headings are suppressed, then that area *	    is used for text.  Room left to punch holes at left. *	2)  Baseline spacing is tightened up for smaller font sizes *	3)  options can now reset each other *	4)  added "-P" option to specifiy output device (for compatibility *	    with lpr system stuff.) *	5)  Improved maha environment variable handling (pair up and eliminate *	    double and single quotes). *	6)  Interpress file now has mode 600 (for security reasons) *	7)  Maximum line length increased. * * 13-Jan-86  Lee Moore (lee) at Xerox Webster Research Center *	Changed a call to strcpyn to strncpy. * *  8-apr-85  ed flint *	conditional compilation for vax11-c (vms) * *  26-mar-85 ed flint @ Xerox, WRC *	add fclose after do_file to prevent running out of open file descriptors */#ifdef vax11c# include stdio# include ssdef# include ctype# include descrip#else# include <stdio.h># include <pwd.h># include <strings.h># include <sys/types.h># include <sys/stat.h># include <sys/time.h>#endif# include "iptokens.h"# include "literal.h"# include "operator.h"/* * the following defines a program that will queue an Interpress master * for printing */# define  QIP		"qip"# define  Break_size	1024# define  Default_universal_prefix	"Xerox/XC1-1-1/"# define  Line_size	192		/* upped from 132 *//* All page boundaries are computed in the 1/10 point co-ordinate system *//* *  Orig_y is an offset from the top of the page.  It must be converted *  to a measurement from the bottom of the page (a calculation that is *  rotation-dependent). */# define  INCH		720# define  Half_INCH	360# define  Sixth_INCH	120			/* one line at 6 lpi */# define  Page_width	(8 * INCH + Half_INCH)# define  Page_length	(11 * INCH)			/* rflg  ?  Landscape mode : Portrait mode */# define  Orig_x	(rflg ? (1.5 * INCH/10) : (9 * INCH/10))# define  Orig_y	(rflg ? (Sixth_INCH * 8) : (Sixth_INCH * 5))# define  Header_to_orig_x	0# define  Header_to_orig_y	(2 * Sixth_INCH)/* Frame variable defines */# define  F_transform	0# define  F_headfont	1# define  F_bodyfont	2# define  F_italicfont	3# define  No	0# define  Yes	1extern int errno;/* enum, perhaps? */typedef char boolean;/* routines that return something other than int */char *strecpy();char *allocate();char *next_arg();char *sbrk();char *getenv();char *itoa();char *rindex();/* option flags */boolean lflg = No;	/* line printer mode */boolean rflg = No;	/* rotation - landscape mode */boolean tflg = No;	/* omit title *//* valued options */int  columns   = 1;char *bodyfont_name = "Vintage-Printwheel/10";char *headfont_name = "Modern-Bold/12";char *italicfont_name = "Modern-Bold-Italic/12";char *banner   = NULL;char *copies   = "1";char *printer  = NULL;			/* destination printer */char *header   = "%f            %t            Page %p, line %l";char *name     = NULL;char *output   = NULL;char *pages    = NULL;#ifdef vax11cchar *template = "IPPXXXXXX";#endif/* *  page characteristics:  these variables define the extremes for the *  current page or column.  'column_separation' is the distance between *  the left sides of each column on the page. */#ifndef notdefint left_margin = (9 * INCH / 10);	/* x origin in portrait mode */#elseint left_margin = Orig_x;#endifint right_margin;int top_margin;int bottom_margin;int column_separation;/* sundries */boolean send_to_printer = Yes;char real_header[256];		/* header built here */char *myname;			/* name invoked with */char *filename;int  *page_select = NULL;	/* array of page selections */int  *curr_page_select;int  page_low;int  page_high;int  ipress_file;		/* interpress file descriptor */int  null_file;			/* fd for /dev/null */int  line_number;int  page_number;int  pages_printed = 0;		/* total pages for this interpress file */int  special_font = 0;		/* fonts that require special handling */int  line_spacing;int  tab_amount = 8;#ifndef vax11cstruct passwd *pwd;		/* passwd entry for this user */struct stat   file_stat;	/* stat of current file */#endif# define  Font_Terminal  1/* current arguments */int  argc;char **argv;/* font structure definition */struct font{    char *ft_universal_name;    char *ft_leaf_name;    int  ft_size;};/* fonts used */struct font headfont;struct font bodyfont;struct font italicfont;main(_argc, _argv)int  _argc;char **_argv;{    char *ptr;		/* temporary pointers used for loops and such */    char *src;    char *dest;    int length;    int i;    FILE *file;		/* file currently processing */#ifdef vax11c    int error;    int retlen;    char command[256];    $DESCRIPTOR(mahadesc,"MAHAENV");    $DESCRIPTOR(cmddesc,command);#endif    /* get our name */    if (_argc < 1)    {	exit(1);    }#ifdef vax11c    myname= _argv[0];#else    if ((myname = rindex(_argv[0], '/')) == NULL)    {	myname = _argv[0];    }    else    {	myname++;    }#endif    /* get the options specified in the environment (defaults) */#ifdef vax11c    if ( (error= lib$get_symbol(&mahadesc,&cmddesc,&retlen)) == SS$_NORMAL )    {	if ( retlen != 0 )	{	    command[retlen & 0xff]= '\0';		/* null terminate string */	    src= command;	/* break the string up into null terminated arguments */	/* half the length is a good upper bound on number of arguments */		argv = (char **)allocate(strlen(src) / 2);		for (argc = 1, ptr = src; *ptr != '\0'; argc++)		{		    while (*ptr == ' ')			ptr++;		    argv[argc] = ptr;		    while (*ptr != ' ' && *ptr != '\0')		    {			if (*ptr == '"')			{			    while (*++ptr != '"' && *ptr != '\0');			}			else if (*ptr == '\'')			{			    while (*++ptr != '\'' && *ptr != '\0');			}			ptr++;		    }		    *ptr++ = '\0';		}	/* terminate the argument list */		argv[argc] = NULL;	/* process the options found in the environment */		get_options();	}    }#else    if ((src = getenv("MAHA")) != NULL)    {	/* break the string up into null terminated arguments */	/* half the length is a good upper bound on number of arguments */	argv = (char **)allocate(strlen(src) / 2);	for (argc = 1, ptr = src; *ptr != '\0'; argc++)	{	    register char *dst;	    char quote;	    while (*ptr == ' ')		ptr++;	    argv[argc] = dst = ptr;	    while (*ptr != ' ' && *ptr != '\0')	    {		if (*ptr == '"' || *ptr == '\'')		{		    quote = *ptr++;	/* Save + skip quote */		    while( *ptr != quote && *ptr != '\0')			*dst++ = *ptr++;		    if (*ptr != '\0')			ptr++;		/* Skip closing quote */		}		else		    *dst++ = *ptr++;	    }	    if (*ptr != '\0')		ptr++;		/* skip 1st trailing space */	    *dst = '\0';	/* end arg. */	}	/* terminate the argument list */	argv[argc] = NULL;	/* process the options found in the environment */	get_options();    }#endif    /* use the real arguments */    argc = _argc;    argv = _argv;    /* process (real) arguments */    get_options();    /* establish and verify the requested fonts */    establish_font(headfont_name, &headfont);    establish_font(bodyfont_name, &bodyfont);    establish_font(italicfont_name, &italicfont);#ifndef vax11c    /* get passwd entry for future reference */    pwd = getpwuid(geteuid());#endif    /* setup output file */    if (output == NULL)    {	/* build a temporary file name */#ifdef vax11c	output= mktemp(template);#else	output = allocate(1 + 5 + 1 + 2 + 1);	(void) sprintf(output, "/tmp/@%d.ip", getpid());#endif    }#ifdef vax11c    if ((ipress_file = creat(output, 0, "rfm=udf")) == -1)#else    if ((ipress_file = creat(output, 0600)) == -1)#endif    {	system_error(output);	exit(1);    }    ip_select(ipress_file);#ifndef vax11c    /* open the null device for throwing away output */    null_file = open("/dev/null", 1);    /* set null strings to default values */    if (name == NULL)    {	/* banner name defaults to full name from gecos field */	name = pwd->pw_gecos;	/* perform expansion and stripping */	if ((ptr = index(name, ',')) != NULL)	{	    *ptr = '\0';	/* this affects pwd->pw_gecos, too! */	}	if (index(name, '&') != NULL)	{	    name = allocate(strlen(name) + strlen(pwd->pw_name) + 1);	    for (src = pwd->pw_gecos, dest = name; *src != '\0'; src++, dest++)	    {		if (*src == '&')		{		    for (ptr = pwd->pw_name; *ptr != '\0'; ptr++)		    {			*dest++ = *ptr;		    }		}		else		{		    *dest = *src;		}	    }	}    }#endif    if (banner == NULL)    {	/* banner defaults to file name(s) */	if (argc == 0)	{	    banner = "out of the blue";	}	else	{	    for (length = 0, i = 0; i < argc; i++)	    {		length += strlen(argv[i]) + 2;	    }	    banner = allocate(length + 1);	    for (ptr = banner, i = 0; i < argc; i++)	    {		ptr = strecpy(ptr, argv[i]);		ptr = strecpy(ptr, ", ");	    }	    ptr -= 2;	    *ptr = '\0';	}    }    /* unravel the page specifiation */    /* we will never need more than strlen(pages) ints to hold the info */    if (pages != NULL)    {	page_select = (int *)allocate(strlen(pages) * sizeof(int));	unravel_pages(pages, page_select);    }    /* write the preamble for the interpress file */    AppendOp(OP_beginBlock);    AppendOp(OP_beginBody);	/* preamble start */    /* setup font definitions in frame */    SetupFont(headfont.ft_universal_name,	      headfont.ft_size * 10.,	      F_headfont);    SetupFont(bodyfont.ft_universal_name,	      bodyfont.ft_size * 10.,	      F_bodyfont);    SetupFont(italicfont.ft_universal_name,	      headfont.ft_size * 10.,		/* use headfont's size */	      F_italicfont);    /* remember special fonts */    if (strcmp(bodyfont.ft_leaf_name, "Terminal") == 0)    {	special_font = Font_Terminal;    }    /* save scaling transform that uses 1/10 point co-ordinate system */    top_margin = (rflg ? Page_width : Page_length) - Orig_y;    if (tflg)		/* the user may not want headings... */	top_margin += Header_to_orig_y; /* use heading area */    bottom_margin = 2 * Sixth_INCH;    right_margin = (rflg ? Page_length : Page_width) - Orig_x;    column_separation = (right_margin - Orig_x) / columns;    line_spacing = (bodyfont.ft_size +		  ((bodyfont.ft_size > 8) ? 2 : 0)) * 10;    if (rflg)    {	/* we need a rotation transform, too */	Rotate(90.);	Translate((double)Page_width, (double)0);    }    AppendRational(353L,10000000L);    AppendOp(OP_scale);    if (rflg)    {	AppendOp(OP_concat);	AppendOp(OP_concat);    }    AppendInteger((long) F_transform);    AppendOp(OP_fset);    AppendOp(OP_endBody);	/* end preamble */    if (argc == 0)    {	/* no filenames -- do standard input */	filename = NULL;	do_file(stdin);    }    for (; argc > 0; argc--, argv++)    {	filename = argv[0];	if (strcmp(filename, "-") == 0)	{	    /* this is really standard input */	    filename = NULL;	    do_file(stdin);	}	else	{	    /* open the file */	    if ((file = fopen(filename, "r")) == NULL)	    {		system_error(filename);	    }	    else	    {		do_file(file);		(void) fclose(file);	    }	}    }    /* wrap up the output */    ip_select(ipress_file);    AppendOp(OP_endBlock);    ip_close();    /* send to the printer */    if (send_to_printer)    {	if (pages_printed == 0)	{	    /* don't print anything but remove temporary */#ifdef vax11c	    delete(output);#else	    (void) unlink(output);#endif	}	else	{#ifdef vax11c	    char buff[256];	    int wait= 0;	    $DESCRIPTOR(buffdesc,buff);	    (void) strcpy(buff,"xpress/noformat ");	    (void) strcat(buff,output);    	    buffdesc.dsc$w_length= strlen(buff);	    if ( (error= lib$spawn(&buffdesc,0,0,&wait)) != SS$_NORMAL )	    {	    	fprintf(stderr,"\nFile %s contains interpress master\n",output);		exit(error);	    }    	    delete(output);#else	    char *buff;   	    /* exec a "qip" to queue the file */	    buff = allocate(strlen(name) + 1 + 1);	    (void) strcpy(buff, "F");	    (void) strcat(buff, name);	    if (printer)		execlp(QIP, "qip", "-q", printer, "-c", copies, "-nc", "-nk",		    "-t", banner, "-x", buff, output, 0);	    else		execlp(QIP, "qip", "-c", copies, "-nc", "-nk",		    "-t", banner, "-x", buff, output, 0);	    fprintf(stderr, "Can't execl the queing program: %s\n", QIP);	    perror(QIP);	    fprintf(stderr, "File %s contains interpress master.\n", output);	    exit(1);#endif	}    }}get_options(){    while (--argc > 0)    {	argv++;	if (!process_arg())	{	    break;	}    }}/* *  unravel_pages(str, spec) - unravel the page range specification in "str" *			       into integer pairs in "spec".  The first two *			       ints in "spec" bound the first range of pages, *			       the next two bound the second range, and so on. *			       The array is terminated with the pair 0, 0. */unravel_pages(str, spec)char *str;int  *spec;{    int last_num = 0;    int this_num = 0;    register char ch;    boolean is_range = No;    boolean bad_spec = No;    boolean done = No;# define    Start_new_num	(last_num = this_num, this_num = 0)    while (!done)    {	if ((ch = *str++) == '\0')	{	    /* set "done" flag and pretend it's the end of a number */	    done = Yes;	    ch = ',';	}	if (ch >= '0' && ch <= '9')	{	    this_num *= 10;	    this_num += ch - '0';	}	else if (ch == '-')	{	    if (this_num < last_num && *str != '\0')	    {		bad_spec = Yes;	    }	    *spec++ = this_num;	    Start_new_num;	    is_range = Yes;	}	else if (ch == ',')	{	    if (this_num < last_num)	    {		bad_spec = Yes;	    }	    *spec++ = this_num;	    if (is_range)	    {		is_range = No;	    }	    else	    {		*spec++ = this_num;	    }	    Start_new_num;	}	else	{	    fprintf(stderr, "%s: bad character in page specification\n",		myname);	    exit(1);	}    }    if (*--spec == 0)    {	*spec = 1 << 15;	/* infinity */    }    if (bad_spec)    {	fprintf(stderr,

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -