Fix dttypes for BSD systems
[oweals/cde.git] / cde / programs / dtudcexch / exportbdf.c
1 /*
2  * CDE - Common Desktop Environment
3  *
4  * Copyright (c) 1993-2012, The Open Group. All rights reserved.
5  *
6  * These libraries and programs are free software; you can
7  * redistribute them and/or modify them under the terms of the GNU
8  * Lesser General Public License as published by the Free Software
9  * Foundation; either version 2 of the License, or (at your option)
10  * any later version.
11  *
12  * These libraries and programs are distributed in the hope that
13  * they will be useful, but WITHOUT ANY WARRANTY; without even the
14  * implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
15  * PURPOSE. See the GNU Lesser General Public License for more
16  * details.
17  *
18  * You should have received a copy of the GNU Lesser General Public
19  * License along with these librararies and programs; if not, write
20  * to the Free Software Foundation, Inc., 51 Franklin Street, Fifth
21  * Floor, Boston, MA 02110-1301 USA
22  */
23 /* $XConsortium: exportbdf.c /main/4 1996/04/10 13:49:20 ageorge $ */
24 /*
25  *  (c) Copyright 1995 FUJITSU LIMITED
26  *  This is source code modified by FUJITSU LIMITED under the Joint
27  *  Development Agreement for the CDEnext PST.
28  *  This is unpublished proprietary source code of FUJITSU LIMITED
29  *
30  *  Authors: Seiya Miyazaki     FUJITSU LIMITED
31  *           Hiroyuki Chiba     FUJITSU LIMITED
32  */
33 #include <stdio.h>
34 #include <fcntl.h>
35 #include <signal.h>
36 #ifndef SVR4
37 #if !defined( SYSV )
38 #include <sys/resource.h>
39 #endif
40 #ifdef __osf__
41 #define _BSD
42 #endif
43 #include <sys/wait.h>
44 #ifdef __osf__
45 #undef _BSD
46 #endif
47 #else
48 #include <wait.h>
49 #endif
50 #include <memory.h>
51 #include <unistd.h>
52 #include <sys/stat.h>
53 #include <sys/types.h>
54 #include <errno.h>
55
56 #include "bdfgpf.h"
57
58 static  int     writeBdfHeader();
59 static  int     readBdfToMemory();
60 static  void    sigint_out();
61 static char     buf[BUFSIZE];
62 static  struct  ptobhead        w_bdf ;
63
64 static  void
65 sigint_out()
66 {
67     fclose(w_bdf.output) ;
68     fclose(w_bdf.input) ;       /* stream */
69     exit( 0 );
70 }
71
72 int
73 expCheckCode( code, code_num, code_list )
74 unsigned int    code ;
75 int     code_num ;
76 int     *code_list ;
77 {
78         int     i ;
79
80         if( code < MIN_CODE || code > MAX_CODE )  return -1 ;
81         for( i=0; i<code_num; i++ ){
82             if( code == code_list[i] )  return 0 ;
83         }
84         return -1 ;
85 }
86
87 int
88 ExpGpftoBDF( gpf_name, bdf_name, code_num, code_list, comment_num, comment_list, make_all )
89 char    *gpf_name ;     /* pointer to GPF file name area        */
90 char    *bdf_name ;     /* pointer to BDF file name area        */
91 int     code_num ;      /* number of GPF code                   */
92 int     *code_list ;    /* pointer to GPF code lists            */
93 int     comment_num ;   /* number comments                      */
94 char    **comment_list ;/* pointer to the list of comments      */
95 int     make_all ;      /* convert whole GPF fomat file to BDF  */
96 {
97         struct  stat    statbuf ;
98         struct  btophead        r_gpf ;
99         int                     rtn, i, num_chars ;
100
101         /*
102          * parameter check
103          */
104         if( gpf_name == NULL || bdf_name == NULL ){
105             fprintf(stderr, "GPF or BDF file name is not specified.\n" ) ;
106             return -1 ;
107         }
108         /*
109          * initiation
110          */
111         memset( &w_bdf, 0, sizeof(struct ptobhead) ) ;
112         memset( &r_gpf, 0, sizeof(struct btophead) ) ;
113
114         if ( stat( SNFTOBDF, &statbuf ) ) {
115             if (!( oakgtobdf = get_cmd_path( getenv( "PATH" ), SNFTOBDF_CMD ))) {
116                 fprintf( stderr, "There is not %s command.\n", SNFTOBDF_CMD ) ;
117                 return -1 ;
118             }
119         }else{
120             oakgtobdf = SNFTOBDF;
121         }
122
123         /*
124          * export glyphs in BDF format
125          */
126         w_bdf.snf_file = gpf_name ;
127         if( (w_bdf.output = fopen( bdf_name, "w" )) == NULL ){
128             fprintf(stderr, "\"%s\" cannot open.\n", bdf_name ) ;
129             return -1 ;
130         }
131         
132         signal( SIGHUP , (void(*)())sigint_out );
133         signal( SIGINT , (void(*)())sigint_out );
134         signal( SIGQUIT, (void(*)())sigint_out );
135         signal( SIGTERM, (void(*)())sigint_out );
136
137         if( (rtn = writeBdfHeader(&w_bdf, comment_num, comment_list)) ){
138             fprintf(stderr, "\"%s\" cannot write header.\n", bdf_name ) ;
139             fclose(w_bdf.output) ;
140             fclose(w_bdf.input) ;       /* stream */
141             return rtn ;
142         }
143         
144         r_gpf.bdf_width         = w_bdf.bdf_width ;
145         r_gpf.bdf_height        = w_bdf.bdf_height ;
146         r_gpf.input             = w_bdf.input ;
147
148         num_chars = ((make_all) ? w_bdf.num_chars : code_num) ;
149
150         if( (r_gpf.code = (int *)malloc( sizeof(int) * num_chars)) == NULL ) {
151             fclose(w_bdf.output) ;
152             fclose(w_bdf.input) ;
153             return(MALLOC_ERROR);
154         }
155
156         if( (r_gpf.ptn = (char **)calloc( num_chars, sizeof(char *) )) == NULL ) {
157             fclose(w_bdf.output) ;
158             fclose(w_bdf.input) ;
159             return(MALLOC_ERROR);
160         }
161
162         if( (rtn = readBdfToMemory(&r_gpf, buf, code_num, code_list, make_all)) ){
163             fprintf(stderr, "\"%s\" cannot read glyph.\n", bdf_name ) ;
164             fclose(w_bdf.output) ;
165             fclose(w_bdf.input) ;
166             return rtn ;
167         }
168         fclose(w_bdf.input) ;
169         wait(0) ;
170
171         w_bdf.zoomf     = 0 ;
172         w_bdf.num_chars = r_gpf.num_chars ;
173         w_bdf.code      = r_gpf.code ;
174         w_bdf.ptn       = r_gpf.ptn  ;
175
176         if( (rtn = WritePtnToBdf( &w_bdf, buf )) ){
177             fprintf(stderr, "\"%s\" cannot write glyph.\n", bdf_name ) ;
178             fclose(w_bdf.output) ;
179             return rtn ;
180         }
181         fclose(w_bdf.output) ;
182         
183         signal( SIGHUP , SIG_IGN );
184         signal( SIGINT , SIG_IGN );
185         signal( SIGQUIT, SIG_IGN );
186         signal( SIGTERM, SIG_IGN );
187
188         /*
189          * free memories
190          */
191         free( r_gpf.code ) ;
192         for(i=0; i<r_gpf.num_chars; i++){
193             if(r_gpf.ptn[i])    free(r_gpf.ptn[i]) ;
194         }
195         free( r_gpf.ptn ) ;
196
197         return 0 ;
198 }
199
200 static  int
201 writeBdfHeader(head, comment_num, comment_list)
202 struct ptobhead *head;
203 int     comment_num ;   /* number comments                      */
204 char    **comment_list ;/* pointer to the list of comments      */
205 {
206         FILE            *fp;
207         int             fd[2];
208         unsigned int    getstat;
209         char            buf[BUFSIZE], *p;
210
211         int             cnt ;
212         int             comflg ;
213         pid_t           chld_pid = 0;
214 #if defined( SVR4 ) || defined( SYSV ) || defined(__FreeBSD__)
215         int             chld_stat ;
216 #else
217         union   wait    chld_stat ;
218 #endif
219
220         if (head->snf_file != NULL) {
221                 if (pipe(fd) != 0) {
222                         return  PIPE_ERROR;
223                 }
224                 switch (chld_pid = fork()) {
225                 case    0:
226                         close(1);
227                         if(dup(fd[1]) < 0) {
228                                 return(DUP_ERROR);
229                         }
230                         close(fd[0]);
231                         close(fd[1]);
232                         execl( oakgtobdf, oakgtobdf, head->snf_file, 0);
233                         return  EXEC_ERROR;
234                 case    -1:
235                         return(FORK_ERROR);
236                 default:
237                         break;
238                 }
239                 close(fd[1]);
240                 if((fp = (FILE *)fdopen(fd[0], "r")) == NULL) {
241                         close( fd[0] );
242                         kill( chld_pid, SIGKILL );
243                         WaitID( chld_pid, chld_stat ) ;
244                         return  FDOPEN_ERROR;
245                 }
246         } else {
247                 return(BDF_OPEN_HEAD);
248         }
249         head->input = fp ;
250         getstat = 0;
251         comflg = 0 ;
252
253         while ( 1 ) {
254                 if (fgets(buf, BUFSIZE, fp) == NULL) {
255                     fclose( fp );
256                     if (head->snf_file != NULL) {
257                         close(fd[0]);
258                         kill( chld_pid, SIGKILL );
259                         WaitID( chld_pid, chld_stat ) ;
260                     }
261                     return(BDF_INVAL);
262                 }
263                 p = buf;
264                 SCAN_TO_NONSP(p);
265
266                 if (!strncmp(p, CHARS, CHARSsz)) {
267                     if ((sscanf(p, "CHARS %d", &(head->num_chars))) != 1 ){
268                         return(BDF_INVAL);
269                     }
270                     getstat |= 0x04;
271                     break;
272                 }
273                 /*
274                  * write user comments
275                  */
276                 if ( !strncmp(p, "FONT", strlen("FONT"))
277                     && comment_list && !comflg
278                 ) {
279                     int i ;
280                     for( i=0; i<comment_num; i++ ){
281                         char    *ep ;
282                         if( (ep = (char *)strchr( comment_list[i], '\n' )) != NULL )
283                             *ep = '\0' ;
284                         if( comment_list[i] == '\0' )   continue ;
285                         fprintf(head->output, "COMMENT %s\n", comment_list[i]);
286                     }
287                     fprintf(head->output, "COMMENT\n");
288                     comflg++ ;
289                 }
290
291                 fprintf(head->output, "%s", buf);
292
293                 if (!strncmp(p, SIZE, SIZEsz)) {
294                     if ((sscanf(p, "SIZE %f%d",
295                         &(head->bdf_point), &(head->bdf_xdpi))) != 2) {
296                         fclose(fp);
297                         if (head->snf_file != NULL) {
298                             close(fd[0]);
299                             kill( chld_pid, SIGKILL );
300                             WaitID( chld_pid, chld_stat ) ;
301                         }
302                         return(BDF_INVAL);
303                     }
304                     getstat |= 0x01;
305                     continue;
306                 }
307                 if (!strncmp(p, FONTBOUNDINGBOX, FONTBOUNDINGBOXsz)) {
308                     if (( cnt = sscanf( p, "FONTBOUNDINGBOX %d%d%d%d", 
309                                 &(head->bdf_width), &(head->bdf_height), 
310                                 &(head->bdf_x), &(head->bdf_y))) != 4
311                     ) {
312                         fclose(fp);
313                         if (head->snf_file != NULL) {
314                             close(fd[0]);
315                             kill( chld_pid, SIGKILL );
316                             WaitID( chld_pid, chld_stat ) ;
317                         }
318                         return  BDF_INVAL;
319                     }
320                     getstat |= 0x02;
321                     continue;
322                 }
323                 get_charset_registry(head, p) ;
324         }
325
326         if (getstat != 0x07) {
327                 return  BDF_INVAL;
328         }
329
330         return  0;
331 }
332
333
334 static  int
335 readBdfToMemory(head, buf, code_num, code_list, make_all)
336 struct btophead *head;
337 char    *buf;
338 int     code_num ;      /* number of GPF code                   */
339 int     *code_list ;    /* pointer to GPF code lists            */
340 int     make_all ;      /* convert whole GPF fomat file to BDF  */
341 {
342         int     code, mwidth, num_char, bsize, rtn;
343         char    *ptn;
344
345         num_char = 0;
346         mwidth = (head->bdf_width + 7) / 8;
347         bsize = mwidth * head->bdf_height;
348         while(1) {
349             if ((rtn = GetBdfCode(head, buf, &code)) < 0) {
350                 return(rtn);    /* contain BDF_INVAL */
351             } else if (rtn == FILE_END) {
352                 head->num_chars = num_char;
353                 break;
354             }
355             if ( !make_all ) {
356                 if ( expCheckCode(code, code_num, code_list) ) {
357                     continue;
358                 }
359             }
360
361             head->code[num_char] = code;
362             if ( ( ptn = head->ptn[num_char++] = (char *)malloc( bsize ) ) == NULL ) {
363                 return(MALLOC_ERROR);
364             }
365
366             if ((rtn = GetBdfPtn(head, buf, ptn, mwidth, bsize)) != 0) {
367                 return(rtn);
368             }
369         }
370         return(0);
371 }
372