xref: /plan9/sys/src/cmd/postscript/common/misc.c (revision 14f51593fd82e19ba95969a8c07ff71131015979)
1 /*
2  * General purpose routines.
3  */
4 
5 #define _BSD_EXTENSION
6 
7 #include <stdio.h>
8 #include <stdlib.h>
9 #include <string.h>
10 #include <unistd.h>
11 #include <ctype.h>
12 #include <sys/types.h>
13 #include <fcntl.h>
14 
15 #include "gen.h"
16 #include "ext.h"
17 #include "path.h"
18 
19 int	nolist = 0;			/* number of specified ranges */
20 int	olist[50];			/* processing range pairs */
21 
22 int
out_list(str)23 out_list(str)
24     char	*str;
25 {
26     int		start, stop;
27 
28 /*
29  * Grab page ranges from str, save them in olist[], and update the nolist
30  * count. Range syntax matches nroff/troff syntax.
31  */
32 
33     while ( *str && nolist < sizeof(olist) - 2 ) {
34 	start = stop = str_convert(&str, 0);
35 
36 	if ( *str == '-' && *str++ )
37 	    stop = str_convert(&str, 9999);
38 
39 	if ( start > stop )
40 	    error(FATAL, "illegal range %d-%d", start, stop, 0);
41 
42 	olist[nolist++] = start;
43 	olist[nolist++] = stop;
44 
45 	if ( *str != '\0' ) str++;
46     }
47     olist[nolist] = 0;
48     return 0;
49 }
50 
in_olist(num)51 in_olist(num)
52     int		num;
53 {
54     int		i;
55 
56 /*
57  * Return ON if num is in the current page range list. Print everything if
58  * there's no list.
59  */
60     if ( nolist == 0 )
61 	return(ON);
62 
63     for ( i = 0; i < nolist; i += 2 )
64 	if ( num >= olist[i] && num <= olist[i+1] )
65 	    return(ON);
66     return(OFF);
67 }
68 
69 int
setencoding(name)70 setencoding(name)
71     char	*name;
72 {
73     char	path[150];
74 
75 /*
76  * Include the font encoding file selected by name. It's a full pathname if
77  * it begins with /, otherwise append suffix ".enc" and look for the file in
78  * ENCODINGDIR. Missing files are silently ignored.
79  */
80 
81     if ( name == NULL )
82 	name = "Default";
83 
84     if ( *name == '/' )
85 	strcpy(path, name);
86     else sprintf(path, "%s/%s.enc", ENCODINGDIR, name);
87 
88     if ( cat(path) == TRUE )
89 	writing = strncmp(name, "UTF", 3) == 0;
90     return 0;
91 }
92 
cat(file)93 cat(file)
94     char	*file;
95 {
96     int		fd_in;
97     int		fd_out;
98     char	buf[512];
99     int		count;
100 
101 /*
102  * Copy *file to stdout. Return FALSE is there was a problem.
103  */
104 
105     fflush(stdout);
106     if ( (fd_in = open(file, O_RDONLY)) == -1 )
107 	return(FALSE);
108     fd_out = fileno(stdout);
109     while ( (count = read(fd_in, buf, sizeof(buf))) > 0 )
110 	write(fd_out, buf, count);
111     close(fd_in);
112     return(TRUE);
113 }
114 
str_convert(str,err)115 str_convert(str, err)
116     char	**str;
117     int		err;
118 {
119     int		i;
120 
121 /*
122  *
123  * Grab the next integer from **str and return its value or err if *str
124  * isn't an integer. *str is modified after each digit is read.
125  *
126  */
127 
128     if ( ! isdigit(**str) )
129 	return(err);
130 
131     for ( i = 0; isdigit(**str); *str += 1 )
132 	i = 10 * i + **str - '0';
133 
134     return(i);
135 }
136 
137 void
error(int kind,char * fmt,...)138 error(int kind, char *fmt, ...)
139 {
140 	char buf[256];
141 	va_list arg;
142 
143 	if (fmt) {
144 		va_start(arg, fmt);
145 		vsnprintf(buf, sizeof buf, fmt, arg);
146 		va_end(arg);
147 		fprintf(stderr, "%s: %s", prog_name, buf);
148 		if (lineno > 0)
149 			fprintf(stderr, " (line %d)", lineno);
150 		if (position > 0)
151 			fprintf(stderr, " (near byte %d)", position);
152 		putc('\n', stderr);
153 	}
154 	if (kind == FATAL && ignore == OFF) {
155 		if (temp_file != NULL)
156 			unlink(temp_file);
157 		exit(x_stat | 01);
158 	}
159 }
160 
161 /*
162  * Signal handler for translators.
163  */
164 void
interrupt(int sig)165 interrupt(int sig)
166 {
167     USED(sig);
168     if ( temp_file != NULL )
169 	unlink(temp_file);
170     exit(1);
171 }
172