Add GNU LGPL headers to all .c .C and .h files
[oweals/cde.git] / cde / programs / dtudcfonted / dtgpftobdf / gpftobdf.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: gpftobdf.c /main/5 1996/11/08 02:04:24 cde-fuj $ */
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
31
32 #include <stdio.h>
33 #include <sys/types.h>
34 #include <sys/stat.h>
35 #include <string.h>
36 #include <fcntl.h>
37 #include <stdlib.h>
38 #include <unistd.h>
39 #include "font.h"
40 #include "misc.h"
41 #include <X11/X.h>
42 #include <X11/Xproto.h>
43 #include <X11/Xmd.h>
44 #include <ctype.h>
45 #include <errno.h>
46 #include "fontstruct.h"
47 #include "snfstruct.h"
48 #include <time.h>
49 #include "bdftosnf.h"
50 #include <memory.h>
51 #if defined( SVR4 )
52 #include <sys/mman.h>
53 #endif
54
55 #include "udccom.h"
56 #include "udcutil.h"
57
58 #define GLYPHPADOPTIONS                 4
59 #define SIZEOF_COMPRESSED_METRIC        5
60
61 #include        "gtobdf.h"
62 #include        "pcf.h"
63
64 typedef struct  pcf_tmp {
65         FontInfoRec     info;
66         int     ntables;
67         PCFTablePtr     tables;
68         int     nprops;
69         FontPropPtr     props;
70         char    *isStringProp;
71         int     str_length;
72         char    *string;
73         int     nbitmaps;
74         CARD32  bmp_fmt;        /* bitOrder ,byteOrder, glyph, scan */
75         CARD32  *offsets;
76         int     sizebitmaps;
77         char    *bitmaps;
78         CARD32  enc_fmt;
79         CARD16  *encodingOffsets;
80         size_t  pcf_bufsz;
81         caddr_t         pcf_buffer;
82
83         /* scale width  */
84         CARD32  swd_fmt ;
85         int     swd_num ;
86         CARD32  *swidth ;
87
88         /* glyph name   */
89         CARD32  glyph_fmt ;
90         unsigned int    glyphs ;
91         int     *glyph_offset ;
92         char    *glyph_name ;
93
94         /* metrics      */
95         int     compress ;
96         CARD32  mtr_fmt ;
97         int     mtr_num ;
98         xCharInfo       *metrics;
99
100 } PcfTmp;
101
102 typedef struct prop_tmp {
103         char    *font_name;
104         FontPropRec     psize;
105         FontPropRec     resolution;
106 } PropTmp;
107
108
109
110 static  char    *readfontfile();
111 static  void    Anafprop();
112 static  void    pSIZE();
113 static  void    pPROPS();
114 static  void    pCHARS();
115 static  void    pfixCHARS();
116 static  int     getarg();
117
118 static  Bool    seekToType() ;
119 static  int     getMetric() ;
120 static  Bool    getAccel() ;
121 static  Bool    getProperties() ;
122 static  int     putPtn() ;
123 static  int     ByteSwap() ;
124 static  int     invertBits() ;
125
126 static  int     getINT16() ;
127 static  int     getINT32() ;
128 static  CARD32  getLSB32();
129 static  char    *make_toptn();
130 static  void    pSIZE_pcf();
131 static  PcfTmp  *openPcfFont();
132 static  void    setProp();
133 static  void    pPROPS_pcf();
134 static  void    pCHARS_pcf();
135 static  void    BitOrderInvert();
136 static  char    *bufp,buf[2048];
137
138 extern int      ChkPcfFontFile();
139
140
141 main( argc,argv )
142 int     argc;
143 char    *argv[];
144 {
145         int         i,k;
146
147
148         char        *fp;                /* font                         */
149         FontInfoRec *fip;               /* font information             */
150         CharInfoRec *cip, *wkcip;       /* character information        */
151         unsigned int glyphstotal;       /* glyph                        */
152         unsigned int charInfoNum ;      /* character information's number */
153         unsigned int charNum;           /* define character number         */
154         char        *glyphPtr;          /* glyph                        */
155         FontPropRec *fpropPtr,*fplistPtr;       /* font property list   */
156         FontPropRec psprop;             /* point size property          */
157         FontPropRec resprop;            /* resolution property          */
158         char        *fpropvnPtr;
159
160         unsigned int fplistNum;         /* font property number         */
161         char        *fontname;          /* fontname                     */
162         time_t      clock;
163         struct      tm *tm;
164         char        tmbuf[80] ;
165
166         char fname[1024];               /* snf filename                 */
167         int  bitorder;                  /* bitorder                     */
168         int byteorder;                  /* byteorder                    */
169         int scanunit;                   /* scanunit                     */
170         int glyphPad ;                  /* glyph                        */
171         int outLevel;                   /* output information level     */
172         int fix;
173
174
175         int     isPcf;
176
177         PcfTmp  *pcf;
178         PropTmp         proptmp;
179         char    *tmpfname;
180         extern  char    *GetRealFileName();
181
182
183         if (getarg(argc,argv,fname,&bitorder,&byteorder,&scanunit,&glyphPad,
184             &outLevel,&fix) != 0) {
185                 exit( -1 );
186         }
187
188         /*
189          *  read to fontfile 
190          */
191         if ( ( tmpfname = GetRealFileName( fname ) ) == NULL ) {
192                 USAGE("dtgpftobdf: cannot refer to substance file.\n" );
193                 exit( -1 );
194         }
195         if ( strcmp( tmpfname, fname ) != 0 ){
196                 strcpy( fname, tmpfname );
197         }
198
199         if ( ChkPcfFontFile( fname ) == 0 ){
200                 /* pcf font */
201                 isPcf = 1;
202                 if ( !( pcf = openPcfFont( fname ) ) ) {
203                         USAGE("dtgpftobdf: cannot open font\n" );
204                         exit( -1 );
205                 }
206         } else {
207                 /* snf font */
208                 isPcf = 0;
209                 if ( ( fp = readfontfile( fname ) ) == (char *)-1 ) {
210                         exit( -1 );
211                 }
212         }
213
214
215         if ( !isPcf ) {
216                 /* SNF format */
217                 COMM_SNF_GETHEADER( fip, fp ) ;
218                 /* font file check */
219                 if ((fip->version1 != fip->version2) || 
220                     (fip->version1 != FONT_FILE_VERSION)) {
221                         USAGE("dtgpftobdf: illegal font version\n");
222                         exit( -1 );
223                 }
224
225                 cip = (CharInfoRec *)((char *)fip + sizeof(FontInfoRec));
226
227                 charInfoNum = (fip->lastCol - fip->firstCol + 1)
228                     *(fip->lastRow - fip->firstRow + 1);
229                 glyphPtr = ((char *)cip) + ( charInfoNum * sizeof(CharInfoRec) );
230
231                 charNum = charInfoNum ;
232                 wkcip = cip ;
233
234                 glyphstotal = fip->maxbounds.byteOffset;
235
236                 glyphPad = (((fip->maxbounds.metrics.rightSideBearing
237                     - fip->maxbounds.metrics.leftSideBearing)+31)/32)*4;
238
239                 if ( fix == TRUE ) {
240                     for ( i = 0; i < charInfoNum; i++ ) {
241                         if ( wkcip->exists == FALSE ) {
242                             charNum-- ;
243                         }
244                         wkcip++;
245                     }
246                 } else {
247                     glyphstotal = 0 ;
248                     for ( i = 0; i < charInfoNum; i++ ) {
249                         if (wkcip->exists == FALSE) {
250                             charNum-- ;
251                             wkcip++;
252                             continue;
253                         }
254                         glyphstotal += (wkcip->metrics.ascent
255                             + wkcip->metrics.descent) * glyphPad;
256                         wkcip++;
257                     }
258                 }
259
260                 fpropPtr = (FontPropRec *)(glyphPtr + glyphstotal);
261                 fpropvnPtr = ((char *)fpropPtr) + (fip->nProps) * sizeof(FontPropRec);
262
263         }
264
265
266         if ( isPcf ) {
267                 setProp( pcf, &proptmp );
268         } else {
269                 fontname = (char *)0;
270                 Anafprop( 
271                     fip, fpropPtr, fpropvnPtr, 
272                     &fontname, &psprop, &resprop, 
273                     &fplistPtr, &fplistNum 
274                     );
275         }
276
277         /*
278          *¡¡output to BDF information
279          */
280         bufp = buf;
281         memcpy(bufp,"STARTFONT 2.1\n",14);
282         bufp += 14;
283         memcpy(bufp,"COMMENT\n",8);
284         bufp += 8;
285         memcpy(bufp,"COMMENT  This BDF was created by dtgpftobdf.\n",45 );
286         bufp += 45 ;
287         memcpy(bufp,"COMMENT\n",8);
288         bufp += 8;
289         time(&clock);
290         tm = localtime(&clock);
291
292         strcpy( tmbuf, asctime(tm) ) ;
293
294         k = sprintf(bufp,"COMMENT    Created date : %s\n",tmbuf );
295         bufp += k-1;
296         memcpy(bufp,"COMMENT\n",8);
297         bufp += 8;
298
299         if ( isPcf ) {
300                 k = sprintf(bufp,"FONT %s\n",proptmp.font_name);
301                 bufp += k;
302                 *bufp = '\0';
303                 fprintf( stdout,"%s",buf );
304                 pSIZE_pcf( &proptmp );
305                 fprintf( stdout,"FONTBOUNDINGBOX %d %d %d %d\n",
306                     pcf->info.maxbounds.metrics.rightSideBearing 
307                     - pcf->info.maxbounds.metrics.leftSideBearing,
308                     pcf->info.maxbounds.metrics.ascent 
309                     + pcf->info.maxbounds.metrics.descent,
310                     pcf->info.maxbounds.metrics.leftSideBearing,
311                     - ( pcf->info.maxbounds.metrics.descent )
312                         );
313                 pPROPS_pcf( pcf );
314                 if ( outLevel == FALSE ) {
315                         pCHARS_pcf( pcf, fix );
316                 }
317         } else {
318                 k = sprintf( bufp,"FONT %s\n",fontname );
319                 bufp += k;
320                 *bufp = '\0';
321                 fprintf( stdout,"%s",buf );
322                 pSIZE( &psprop, &resprop );
323                 fprintf( stdout,"FONTBOUNDINGBOX %d %d %d %d\n",
324                     cip->metrics.rightSideBearing 
325                     - cip->metrics.leftSideBearing,
326                     cip->metrics.ascent + cip->metrics.descent,
327                     cip->metrics.leftSideBearing,
328                     -(cip->metrics.descent)
329                         );
330                 pPROPS( fip,fplistPtr,fplistNum );
331                 if ( outLevel == FALSE ) {
332                     if ( fix == TRUE ) {
333                         pfixCHARS( fip,cip,glyphPtr,charNum, glyphPad );
334                     } else {
335                         pCHARS(fip,cip,glyphPtr,charNum,glyphPad);
336                     }
337                 }
338
339         }
340
341         fprintf( stdout,"ENDFONT\n" );
342         exit( 0 );
343 }
344
345 /*
346  * read to font file
347  *
348  */
349 static  char    *readfontfile( fname )
350 char    *fname;
351 {
352         int     fd;
353         char    *fp;
354         struct stat stat;
355
356         fd = open( fname,O_RDONLY );
357         if ( fd < 0 ) {
358                 USAGE("dtgpftobdf: can't open file.\n" );
359                 return  ( char * )-1;
360         }
361 #if defined( SVR4 )
362         if ( fstat( fd,&stat ) == 0 ) {
363                 fp = (char *)mmap( 0, stat.st_size, PROT_READ, MAP_SHARED, fd, 0 );
364                 if ( fp == (char *)-1 ) {
365                         if ( ( fp = ( char * )malloc( stat.st_size ) ) == NULL ) {
366                                 USAGE("dtgpftobdf: malloc error.\n" );
367                                 close( fd );
368                                 return  ( char * )-1;
369                         }
370 /*                      if ( read( fd, fp, stat.st_size ) < 0 ) {*/
371                         if ( read( fd, fp, stat.st_size ) != stat.st_size ) {
372                                 USAGE("dtgpftobdf: can't read file.\n" );
373                                 close( fd );
374                                 return  ( char * )-1;
375                         }
376                 }
377         } else {
378                 USAGE("dtgpftobdf: can't read file\n" );
379                 close( fd );
380                 return  ( char * )-1;
381         }
382         close( fd );
383 #else   /* pfa */
384         if ( fstat(fd,&stat) == 0 ) {
385                 if ( ( fp = (char *)malloc(stat.st_size) ) == NULL ) {
386                         USAGE("dtgpftobdf: malloc error.\n" );
387                         close( fd );
388                         return  ( char * )-1;
389                 }
390                 if ( read( fd, fp, stat.st_size ) < 0 ) {
391                         USAGE("dtgpftobdf: can't read file.\n" );
392                         close( fd );
393                         return  ( char * )-1;
394                 }
395         } else {
396                 USAGE("dtgpftobdf: can't read file\n" );
397                 close( fd );
398                 return  ( char * )-1;
399         }
400         close( fd );
401 #endif /* pfa */
402         return  fp;
403 }
404
405
406 #define getINT8( p ) ( *p++ ) ;
407
408 static CARD32
409 getLSB32( p )
410 unsigned char *p;
411 {
412         CARD32  c;
413
414         c = *p++;
415         c |= (CARD32)(*p++) << 8;
416         c |= (CARD32)(*p++) << 16;
417         c |= (CARD32)(*p) << 24;
418
419         return  c;
420 }
421
422
423 static int
424 getINT32( p, format )
425 unsigned char   *p;
426 CARD32  format;
427 {
428         CARD32  c;
429
430         if ( PCF_BYTE_ORDER(format) == MSBFirst ) {
431                 c = (CARD32)(*p++) << 24;
432                 c |= (CARD32)(*p++) << 16;
433                 c |= (CARD32)(*p++) << 8;
434                 c |= (CARD32)(*p);
435         } else {
436                 c = (CARD32)(*p++);
437                 c |= (CARD32)(*p++) << 8;
438                 c |= (CARD32)(*p++) << 16;
439                 c |= (CARD32)(*p) << 24;
440         }
441
442         return ( int )c;
443 }
444
445 static int
446 getINT16( p, format )
447 unsigned char   *p;
448 CARD32  format;
449 {
450         CARD32  c;
451
452         if ( PCF_BYTE_ORDER(format) == MSBFirst ) {
453                 c = (CARD32)(*p++) << 8;
454                 c |= (CARD32)(*p);
455         } else {
456                 c = (CARD32)(*p++);
457                 c |= (CARD32)(*p) << 8;
458         }
459
460         return ( int )c;
461 }
462
463 static Bool
464 seekToType( tables, ntables, type, formatp, sizep, offsetp)
465 PCFTablePtr     tables;
466 int     ntables;
467 CARD32  type;
468 CARD32  *formatp;
469 CARD32  *sizep;
470 CARD32  *offsetp;
471 {
472         int     i;
473
474         for ( i = 0; i < ntables; i++ ) {
475                 if ( getLSB32( (unsigned char *)&tables[i].type) == type) {
476                         *formatp = getLSB32( (unsigned char *)&tables[i].format);
477                         *sizep = getLSB32( (unsigned char *)&tables[i].size);
478                         *offsetp = getLSB32( (unsigned char *)&tables[i].offset);
479                         return  TRUE;
480                 }
481         }
482         return  FALSE;
483 }
484
485
486 static
487 getMetric( buf, format, metric )
488 caddr_t         buf;
489 CARD32  format;
490 xCharInfo       *metric;
491 {
492         metric->leftSideBearing = getINT16( (unsigned char *)buf, format);
493         buf += 2;
494         metric->rightSideBearing = getINT16( (unsigned char *)buf, format);
495         buf += 2;
496         metric->characterWidth = getINT16( (unsigned char *)buf, format);
497         buf += 2;
498         metric->ascent = getINT16( (unsigned char *)buf, format);
499         buf += 2;
500         metric->descent = getINT16( (unsigned char *)buf, format);
501         buf += 2;
502         metric->attributes = getINT16( (unsigned char *)buf, format);
503         buf += 2;
504 }
505
506 static Bool
507 getAccel( pFontInfo, maxink, buf_top, tables, ntables, type )
508 FontInfoPtr     pFontInfo;
509 xCharInfo       *maxink;
510 caddr_t         buf_top;
511 PCFTablePtr     tables;
512 int     ntables;
513 CARD32  type;
514 {
515         CARD32  format;
516         CARD32  size;
517         CARD32  offset;
518         caddr_t         buffer;
519
520         if ( !seekToType( tables, ntables, type, &format, &size, &offset)) {
521                 return  FALSE;
522         }
523
524         buffer = buf_top + offset;
525         format = getLSB32( (unsigned char *)buffer);
526         buffer += 4;
527         if ( !PCF_FORMAT_MATCH( format, PCF_DEFAULT_FORMAT )
528             && !PCF_FORMAT_MATCH( format, PCF_ACCEL_W_INKBOUNDS )
529             ) {
530                 return  FALSE;
531         }
532         pFontInfo->noOverlap = *buffer++;
533         pFontInfo->constantMetrics = *buffer++;
534         pFontInfo->terminalFont = *buffer++;
535         pFontInfo->constantWidth = *buffer++;
536         pFontInfo->inkInside = *buffer++;
537         pFontInfo->inkMetrics = *buffer++;
538         pFontInfo->drawDirection = *buffer++;
539         /* natural alignment */
540
541         buffer++;
542
543         pFontInfo->fontAscent = getINT32( (unsigned char *)buffer, format);
544         buffer += 4;
545
546         pFontInfo->fontDescent = getINT32((unsigned char *)buffer, format);
547         buffer +=4;
548
549         buffer += 4;
550
551         getMetric(buffer, format, &pFontInfo->minbounds.metrics);
552         buffer += 12;
553
554         getMetric(buffer, format, &pFontInfo->maxbounds.metrics);
555         buffer += 12;
556
557         if ( PCF_FORMAT_MATCH( format, PCF_ACCEL_W_INKBOUNDS ) ) {
558                 buffer += 12;
559                 getMetric( buffer, format, maxink);
560         } else {
561                 *maxink = pFontInfo->maxbounds.metrics;
562         }
563
564         return  TRUE;
565 }
566
567 static Bool
568 getProperties( pcf, buf_top, tables, ntables)
569 PcfTmp  *pcf;
570 caddr_t         buf_top;
571 PCFTablePtr     tables;
572 int     ntables;
573 {
574         CARD32  format;
575         CARD32  size;
576         CARD32  offset;
577         caddr_t         buffer;
578         int     i;
579
580         if ( !seekToType( tables, ntables, (CARD32)PCF_PROPERTIES, &format, &size, &offset ) ) {
581                 return  FALSE;
582         }
583
584         buffer = buf_top + offset;
585         format = getLSB32( (unsigned char *)buffer );
586         buffer += 4;
587         if ( !PCF_FORMAT_MATCH( format, PCF_DEFAULT_FORMAT ) ) {
588                 return  FALSE;
589         }
590         pcf->nprops = getINT32((unsigned char *)buffer, format);
591         buffer += 4;
592
593         if ( !( pcf->props = ( FontPropPtr )malloc( pcf->nprops * sizeof( FontPropRec ) ) ) ) {
594                 return  FALSE;
595         }
596
597         if ( !( pcf->isStringProp = ( char * )malloc(pcf->nprops * sizeof( char ) ) ) ) {
598                 return  FALSE;
599         }
600
601         for ( i = 0; i < pcf->nprops; i++ ) {
602                 pcf->props[i].name = getINT32((unsigned char *)buffer, format);
603                 buffer += 4;
604                 pcf->isStringProp[i] = *buffer++;
605                 pcf->props[i].value = getINT32((unsigned char *)buffer, format);
606                 buffer += 4;
607         }
608         if ( pcf->nprops & 3 ) {
609                 i = 4 - (pcf->nprops & 3);
610                 buffer += i;
611         }
612
613         pcf->str_length = getINT32((unsigned char *)buffer, format);
614         buffer += 4;
615
616         pcf->string = (char *)buffer;
617         return  TRUE;
618 }
619
620
621 static  PcfTmp  *
622 openPcfFont( fontname )
623 char    *fontname;
624 {
625         PcfTmp  *pcf_tmp;
626
627         CARD32  format;
628         CARD32  size;
629         CARD32  offset;
630         CARD32  *bitmapSizes;
631         xCharInfo       maxink;
632         caddr_t         buffp;
633         struct stat     st;
634
635         pcf_tmp = ( PcfTmp * )calloc( 1, sizeof( PcfTmp ) );
636         if ( !pcf_tmp ) {
637                 USAGE("dtgpftobdf : calloc() error.\n" ) ;
638                 goto Bail;
639         }
640
641         if ( stat( fontname, &st ) ) {
642                 goto Bail;
643         }
644
645         if ( ( pcf_tmp->pcf_buffer = readfontfile( fontname)) == (char *)-1 ) {
646                 goto Bail;
647         }
648
649         pcf_tmp->pcf_bufsz = st.st_size;
650
651         if ( (format = getLSB32( (unsigned char *)pcf_tmp->pcf_buffer )) != PCF_FILE_VERSION ) {
652                 USAGE1("dtgpftobdf : pcf file version(0x%x) error.\n", format ) ;
653                 goto Bail;
654         }
655
656         pcf_tmp->ntables = getLSB32( (unsigned char *)(pcf_tmp->pcf_buffer + 4) );
657         pcf_tmp->tables = (PCFTablePtr)(pcf_tmp->pcf_buffer + 8 );
658
659         if ( !getAccel( 
660             &pcf_tmp->info, &maxink, pcf_tmp->pcf_buffer,
661             pcf_tmp->tables, pcf_tmp->ntables, (CARD32)PCF_BDF_ACCELERATORS
662             )
663             ) {
664                 if ( !getAccel( 
665                     &pcf_tmp->info, &maxink, pcf_tmp->pcf_buffer,
666                     pcf_tmp->tables, pcf_tmp->ntables, (CARD32)PCF_ACCELERATORS
667                     )
668                     ) {
669                         USAGE("dtgpftobdf : Cannot get accelerators.\n" ) ;
670                         goto Bail;
671                 }
672         }
673
674         if ( !getProperties( 
675             pcf_tmp, pcf_tmp->pcf_buffer, 
676             pcf_tmp->tables, pcf_tmp->ntables
677             )
678             ) {
679                 USAGE("dtgpftobdf : getProperties error.\n" ) ;
680                 goto Bail;
681         }
682         if ( !seekToType( 
683             pcf_tmp->tables, pcf_tmp->ntables, 
684             (CARD32)PCF_BITMAPS, &format, &size, &offset
685             )
686             ) {
687                 USAGE("dtgpftobdf : PCF_BITMAPS error.\n" ) ;
688                 goto Bail;
689         }
690
691         buffp = pcf_tmp->pcf_buffer + offset;
692
693         format = getLSB32( (unsigned char *)buffp);
694         buffp += 4;
695
696         if ( !PCF_FORMAT_MATCH( format, PCF_DEFAULT_FORMAT ) ) {
697                 USAGE("dtgpftobdf : error.!PCF_FORMAT_MATCH(PCF_BITMAPS)\n" ) ;
698                 goto Bail;
699         }
700
701         pcf_tmp->nbitmaps = getINT32( (unsigned char *)buffp, format);
702         buffp += 4;
703         pcf_tmp->offsets = (CARD32 *)buffp;
704         buffp += sizeof( *pcf_tmp->offsets) * pcf_tmp->nbitmaps;
705
706
707         bitmapSizes = (CARD32 *)buffp;
708         pcf_tmp->sizebitmaps 
709             = getINT32( (unsigned char *)&bitmapSizes[PCF_GLYPH_PAD_INDEX(format)], format);
710         pcf_tmp->bmp_fmt = format;
711         buffp += sizeof( *bitmapSizes) * GLYPHPADOPTIONS;
712         pcf_tmp->bitmaps = buffp;
713         buffp += pcf_tmp->sizebitmaps;
714
715         if ( !seekToType( 
716             pcf_tmp->tables, pcf_tmp->ntables, 
717             (CARD32)PCF_BDF_ENCODINGS, &format, &size, &offset
718             )
719             ) {
720                 USAGE("dtgpftobdf : error.(PCF_BDF_ENCODINGS)\n" ) ;
721                 goto Bail;
722         }
723
724         buffp = pcf_tmp->pcf_buffer + offset;
725         format = getLSB32( (unsigned char *)buffp);
726         buffp += 4;
727         if ( !PCF_FORMAT_MATCH( format, PCF_DEFAULT_FORMAT ) ) {
728                 USAGE("dtgpftobdf : error.!PCF_FORMAT_MATCH(PCF_BDF_ENCODINGS)\n" ) ;
729                 goto Bail;
730         }
731
732         pcf_tmp->info.firstCol = getINT16( (unsigned char *)buffp, format);
733         buffp += 2;
734         pcf_tmp->info.lastCol = getINT16( (unsigned char *)buffp, format);
735         buffp += 2;
736         pcf_tmp->info.firstRow = getINT16( (unsigned char *)buffp, format);
737         buffp += 2;
738         pcf_tmp->info.lastRow = getINT16( (unsigned char *)buffp, format);
739         buffp += 2;
740         pcf_tmp->info.chDefault = getINT16( (unsigned char *)buffp, format);
741         buffp += 2;
742
743         pcf_tmp->info.allExist  = FALSE;
744         pcf_tmp->enc_fmt = format;
745         pcf_tmp->encodingOffsets = (CARD16 *)buffp;
746
747         /*
748         * get scale width infomations 
749         */
750         if ( !seekToType( 
751             pcf_tmp->tables, pcf_tmp->ntables, 
752             (CARD32)PCF_SWIDTHS, &format, &size, &offset
753             )
754             ) {
755                 goto Bail;
756         }
757
758         buffp = pcf_tmp->pcf_buffer + offset;
759         format = getLSB32( (unsigned char*)buffp);
760         buffp += 4;
761         if ( !PCF_FORMAT_MATCH( format, PCF_DEFAULT_FORMAT ) ) {
762                 goto Bail;
763         }
764         pcf_tmp->swd_fmt = (CARD32)format ;
765         pcf_tmp->swd_num = getINT32( (unsigned char*)buffp, format ) ;
766         buffp += 4;
767
768         pcf_tmp->swidth = (CARD32 *)buffp ;
769
770         /*
771         * get glyph names
772         */
773         if ( !seekToType( 
774             pcf_tmp->tables, pcf_tmp->ntables, 
775             (CARD32)PCF_GLYPH_NAMES, &format, &size, &offset
776             )
777             ) {
778                 goto Bail;
779         }
780
781         buffp = pcf_tmp->pcf_buffer + offset;
782         format = getLSB32( (unsigned char*)buffp);
783         buffp += 4;
784         if ( !PCF_FORMAT_MATCH( format, PCF_DEFAULT_FORMAT ) ) {
785                 goto Bail;
786         }
787         pcf_tmp->glyphs = getINT32( (unsigned char*)buffp, format ) ;
788         buffp += 4;
789         pcf_tmp->glyph_offset = (int *)buffp ;
790         buffp += 4 * (pcf_tmp->glyphs + 1) ;
791         pcf_tmp->glyph_name = (char *)buffp ;
792         pcf_tmp->glyph_fmt = (CARD32)format ;
793
794         /*
795         * get metrics
796         */
797         if ( !seekToType( 
798             pcf_tmp->tables, pcf_tmp->ntables, 
799             (CARD32)PCF_METRICS, &format, &size, &offset
800             )
801             ) {
802                 goto Bail;
803         }
804
805         buffp = pcf_tmp->pcf_buffer + offset;
806         format = getLSB32( (unsigned char*)buffp);
807         buffp += 4;
808         if ( PCF_FORMAT_MATCH( format, PCF_DEFAULT_FORMAT ) ) {
809             pcf_tmp->compress = 0 ;
810             pcf_tmp->mtr_num = getINT32( (unsigned char*)buffp, format ) ;
811             buffp += 4;
812         }else if ( PCF_FORMAT_MATCH( format, PCF_COMPRESSED_METRICS ) ) {
813             pcf_tmp->compress = 1 ;
814             pcf_tmp->mtr_num = (int)getINT16( (unsigned char*)buffp, format ) ;
815             buffp += 2;
816         }else{
817                 goto Bail;
818         }
819         pcf_tmp->metrics = (xCharInfo *)buffp ;
820         pcf_tmp->mtr_fmt = (CARD32)format ;
821
822         return  pcf_tmp;
823
824 Bail:
825         if ( pcf_tmp ) {
826                 free( pcf_tmp );
827         }
828         return  NULL;
829 }
830
831
832 static  void
833 Anafprop(fip,fpropPtr,fpropvnPtr,fontname,ps,res,fplistPtr,fplistNum)
834 FontInfoRec             *fip;
835 FontPropRec     *fpropPtr;
836 char    *fpropvnPtr;
837 char    **fontname;
838 FontPropRec     **fplistPtr;
839 FontPropRec     *ps;
840 FontPropRec     *res;
841 unsigned int    *fplistNum;
842 {
843         FontPropRec     *wkp ,*wklp;
844         int     i, fpnL;
845         char    *fpnp;
846
847         *fplistNum = fip->nProps - 1;
848         *fplistPtr = (FontPropRec *)malloc(*fplistNum * sizeof(FontPropRec));
849         wkp = fpropPtr;
850         wklp = *fplistPtr;
851         for (i = 0; i < fip->nProps; i++) {
852                 fpnp = fpropvnPtr + wkp->name;
853                 fpnL = strlen(fpnp);
854                 if ((fpnL == 4) && (strncmp(fpnp,"FONT",4) == 0)) {
855                         *fontname = fpropvnPtr + wkp->value;
856                         wkp++;
857                         continue;
858                 }
859                 if (fpnL == 10) {
860                         if (strncmp(fpnp,"POINT_SIZE",10) == 0) {
861                                 ps->value = wkp->value;
862                         }
863                         if (strncmp(fpnp,"RESOLUTION",10) == 0) {
864                                 res->value = wkp->value;
865                         }
866                 }
867                 wklp->name = (CARD32)fpropvnPtr + wkp->name;
868                 if (wkp->indirect == TRUE) {
869                         wklp->value = (INT32)fpropvnPtr + wkp->value;
870                 } else {
871                         wklp->value = wkp->value;
872                 }
873                 wklp->indirect = wkp->indirect;
874                 wkp++;
875                 wklp++;
876         }
877 }
878
879
880
881 static void
882 setProp( pcf, proptmp )
883 PcfTmp  *pcf;
884 PropTmp         *proptmp;
885 {
886         int     i, fpnL;
887         char    *fpnp;
888
889         for ( i = 0; i < pcf->nprops; i++ ) {
890                 fpnp = pcf->string + pcf->props[i].name;
891                 fpnL = strlen(fpnp);
892                 if ( ( fpnL == 4 ) && ( strncmp( fpnp,"FONT", 4 ) == 0 ) ) {
893                         proptmp->font_name = pcf->string + pcf->props[i].value;
894                         continue;
895                 }
896                 if ( fpnL == 10 ) {
897                         if ( strncmp( fpnp,"POINT_SIZE", 10 ) == 0 ) {
898                                 proptmp->psize.value = pcf->props[i].value;
899                         } else if ( strncmp( fpnp, "RESOLUTION", 10 ) == 0 ) {
900                                 proptmp->resolution.value = pcf->props[i].value;
901                         }
902                 }
903         }
904 }
905
906
907
908 /*
909  *  output to SIZE (SIZE point resolutionX resolutionY) 
910  * 
911  */
912 static  void
913 pSIZE( ps, res )
914 FontPropRec *ps, *res;
915 {
916         int     k;
917         float   f;
918         char    buf1[16], buf2[16];
919
920         f = ps->value / 10.0;
921         if ( ( ps->value % 10 ) != 0 ) {
922                 sprintf( buf1, "%.1f", f );
923         } else {
924                 sprintf( buf1, "%.0f", f );
925         }
926         k = ( ( res->value * 72.27 ) / 100.0 ) + 1;
927         sprintf( buf2, "%d %d", k, k );
928         fprintf( stdout, "SIZE %s %s\n", buf1, buf2 );
929         return;
930 }
931
932
933 /* output to SIZE of pcf font */
934
935 static void     
936 pSIZE_pcf( proptmp )
937 PropTmp         *proptmp;
938 {
939         int     k;
940         float   f;
941         char    buf1[16],buf2[16];
942
943         f = proptmp->psize.value / 10.0;
944         if ( ( proptmp->psize.value % 10 ) != 0 ) {
945                 sprintf( buf1,"%.1f",f );
946         } else {
947                 sprintf(buf1,"%.0f",f);
948         }
949         k = ( ( proptmp->resolution.value * 72.27 ) / 100.0 ) + 1;
950         sprintf( buf2, "%d %d", k, k );
951         fprintf( stdout,"SIZE %s %s\n", buf1, buf2 );
952         return;
953 }
954
955
956
957 static  void
958 pPROPS( fip,fplistPtr,fplistNum )
959 FontInfoRec     *fip;
960 FontPropRec     *fplistPtr;
961 unsigned int    fplistNum;
962 {
963         FontPropRec     *wkp;
964         int     i, k;
965
966         bufp = buf;
967         k = sprintf( bufp,"STARTPROPERTIES %d\n", fplistNum+3 );
968         bufp += k;
969         k = sprintf( bufp, "FONT_ASCENT %d\n", fip->fontAscent );
970         bufp += k;
971         k = sprintf( bufp, "FONT_DESCENT %d\n", fip->fontDescent );
972         bufp += k;
973         k = sprintf( bufp, "DEFAULT_CHAR %d\n", fip->chDefault );
974         bufp += k;
975         wkp = fplistPtr;
976         for ( i = 0; i < fplistNum; i++ ) {
977                 if ( wkp->indirect == TRUE ) {
978                         k = sprintf( bufp, "%s \"%s\"\n", wkp->name, wkp->value );
979                         bufp += k;
980                 } else {
981                         k = sprintf( bufp, "%s %d\n", wkp->name, wkp->value );
982                         bufp += k;
983                 }
984                 wkp++;
985         }
986         k = sprintf( bufp, "ENDPROPERTIES\n" );
987         bufp += k;
988         *bufp = '\0';
989         fprintf( stdout, "%s", buf );
990         return;
991
992 }
993
994
995 /* output to font property information of pcf fontpcf */
996 static  void    
997 pPROPS_pcf( pcf )
998 PcfTmp  *pcf;
999 {
1000         FontPropPtr     wkp;
1001         int     i, k;
1002
1003         bufp = buf;
1004         k = sprintf( bufp, "STARTPROPERTIES %d\n", pcf->nprops+3 );
1005         bufp += k;
1006         k = sprintf( bufp, "FONT_ASCENT %d\n", 
1007             (pcf->info.fontAscent >= pcf->info.maxbounds.metrics.ascent)
1008             ? pcf->info.fontAscent : pcf->info.maxbounds.metrics.ascent
1009             );
1010         bufp += k;
1011         k = sprintf( bufp, "FONT_DESCENT %d\n",
1012             (pcf->info.fontDescent >= pcf->info.maxbounds.metrics.descent)
1013             ? pcf->info.fontDescent : pcf->info.maxbounds.metrics.descent
1014             );
1015         bufp += k;
1016         k = sprintf( bufp, "DEFAULT_CHAR %d\n", pcf->info.chDefault );
1017         bufp += k;
1018         wkp = pcf->props;
1019         for ( i = 0; i < pcf->nprops; i++ ) {
1020                 if ( pcf->isStringProp[i] ) {
1021                         k = sprintf(bufp,"%s \"%s\"\n", 
1022                             pcf->string + wkp->name, pcf->string + wkp->value
1023                             );
1024                         bufp += k;
1025                 } else {
1026                         k = sprintf(bufp,"%s %d\n", 
1027                             pcf->string + wkp->name, wkp->value
1028                             );
1029                         bufp += k;
1030                 }
1031                 wkp++;
1032         }
1033         k = sprintf( bufp, "ENDPROPERTIES\n" );
1034         bufp += k;
1035         *bufp = '\0';
1036         fprintf( stdout,"%s",buf );
1037         return;
1038
1039 }
1040
1041
1042
1043 /*
1044  * output to character information and patern
1045  *
1046  */
1047 static  void    
1048 pCHARS(fip,cip,glyphPtr,charNum,glyphPad)
1049 FontInfoRec     *fip;
1050 CharInfoRec     *cip;
1051 char    *glyphPtr;
1052 unsigned int    charNum;
1053 unsigned int    glyphPad;
1054
1055 {
1056         CharInfoRec     *wkp;
1057         int     i, j;
1058         unsigned int    frow, lrow, row, fcol, lcol, col;
1059         unsigned int    bbw, bbh;
1060         unsigned int    bml;
1061         char    *glyph;
1062
1063         fprintf( stdout, "CHARS %d\n", charNum );
1064
1065         frow = fip->firstRow;
1066         lrow = fip->lastRow;
1067         fcol = fip->firstCol;
1068         lcol = fip->lastCol;
1069         wkp = cip;
1070         glyph = glyphPtr;
1071         row = frow;
1072
1073         for ( i = 0; i < 256; i++ ) {
1074                 cvtp[i] = &cvt[i];
1075         }
1076
1077         for ( row = frow; row <= lrow; row++ ) {
1078                 for ( col = fcol; col <= lcol; col++ ) {
1079                         if ( wkp->exists == FALSE ) {
1080                                 wkp++;
1081                                 continue;
1082                         }
1083                         fprintf( stdout, "STARTCHAR %.2x%.2x\n", row,col );
1084                         fprintf( stdout, "ENCODING %d\n", (row << 8) + col );
1085                         fprintf( stdout, "SWIDTH 256 0\nDWIDTH %d %d\n",
1086                             wkp->metrics.characterWidth,0 );
1087                         bbw = wkp->metrics.rightSideBearing
1088                             - wkp->metrics.leftSideBearing;
1089                         bbh = wkp->metrics.ascent + wkp->metrics.descent;
1090                         fprintf( stdout, "BBX %d %d %d %d\nBITMAP\n", bbw, bbh,
1091                             wkp->metrics.leftSideBearing,
1092                             - ( wkp->metrics.descent ));
1093                         bml = (bbw + 7) / 8;
1094                         for ( i = 0; i < bbh; i++ ) {
1095                                 bufp = buf;
1096                                 for ( j = 0; j < bml; j++ ) {
1097                                         sprintf( bufp, "%s", cvtp[(unsigned char)glyph[j]] );
1098                                         bufp += 2;
1099                                 }
1100                                 fprintf( stdout, "%.*s\n", bml*2, buf );
1101                                 glyph += glyphPad;
1102                         }
1103                         fprintf( stdout,"ENDCHAR\n" );
1104                         wkp++;
1105                 }
1106         }
1107         return;
1108 }
1109
1110
1111 /*
1112  * output to character information and patern
1113  *
1114  */
1115 static  void    
1116 pfixCHARS(fip,cip,glyphPtr,charNum,glyphPad)
1117 FontInfoRec     *fip;
1118 CharInfoRec     *cip;
1119 char    *glyphPtr;
1120 unsigned int    charNum;
1121 unsigned int    glyphPad;
1122 {
1123         CharInfoRec     *wkp;
1124         register int    i, j, k;
1125         unsigned int    frow,lrow,fcol,lcol;
1126         register int    row, col;
1127         unsigned int    bbw, bbh, bbox, bboy;
1128         unsigned int    xd, yd;
1129         unsigned int    bml;
1130         register char   *glyph;
1131         char    fixbuf[240], *fixbufp;
1132         int     fixdl;
1133
1134         fprintf( stdout,"CHARS %d\n",charNum );
1135
1136         for ( i = 0; i < 256; i++ ) {
1137                 cvtp[i] = &cvt[i];
1138         }
1139
1140         frow = fip->firstRow;
1141         lrow = fip->lastRow;
1142         fcol = fip->firstCol;
1143         lcol = fip->lastCol;
1144         xd =  cip->metrics.characterWidth;
1145         yd = 0;
1146         bbw = cip->metrics.rightSideBearing - cip->metrics.leftSideBearing;
1147         bbh = cip->metrics.ascent + cip->metrics.descent;
1148         bbox = cip->metrics.leftSideBearing;
1149         bboy = -(cip->metrics.descent);
1150
1151         fixbufp = fixbuf;
1152         fixdl = sprintf( fixbufp, "SWIDTH 256 0\nDWIDTH %d %d\n", xd, yd );
1153         fixbufp += fixdl;
1154         k = sprintf(fixbufp,"BBX %d %d %d %d\nBITMAP\n", 
1155             bbw, bbh, bbox, bboy 
1156             );
1157         fixdl += k;
1158
1159         bml = (bbw + 7) / 8;
1160         wkp = cip;
1161         glyph = glyphPtr;
1162         for ( row = frow; row <= lrow; row++ ) {
1163                 for ( col = fcol; col <= lcol; col++ ) {
1164                         if ( wkp->exists == FALSE ) {
1165                                 wkp++;
1166                                 continue;
1167                         }
1168                         bufp = buf;
1169                         memcpy(bufp,"STARTCHAR ",10);
1170                         bufp += 10;
1171                         memcpy(bufp,cvtp[row],2);
1172                         bufp += 2;
1173                         memcpy(bufp,cvtp[col],3);
1174                         bufp += 3;
1175                         memcpy(bufp,"ENCODING ",9);
1176                         bufp += 9;
1177                         k = sprintf(bufp,"%d\n",(row << 8) + col);
1178                         bufp += k;
1179                         memcpy(bufp,fixbuf,fixdl);
1180                         bufp += fixdl;
1181                         for (i = 0; i < bbh; i++) {
1182                                 for (j = 0; j < bml; j++) {
1183                                         memcpy(bufp, cvtp[(unsigned char)glyph[j]],3);
1184                                         bufp += 2;
1185                                 }
1186                                 bufp ++;
1187                                 glyph += glyphPad;
1188                         }
1189                         memcpy( bufp, "ENDCHAR\n", 8 );
1190                         bufp += 8;
1191                         *bufp = '\0';
1192                         fprintf( stdout, "%s", buf );
1193                         wkp++;
1194                 }
1195         }
1196         return;
1197 }
1198
1199
1200 static  
1201 putPtn( bits, width, height)
1202 unsigned char   *bits;          /* 1 byte boundary , no byte swap data */
1203 int     width, height;
1204 {
1205         int     bytewidth;
1206         int     i, j;
1207
1208         bytewidth = ( width + 7) / 8;
1209
1210         for ( i = height; i-- > 0;) {
1211                 for ( j = bytewidth; j-- > 0; bits++) {
1212                         fprintf(stdout, "%.2x", *bits);
1213                 }
1214                 fprintf(stdout, "\n");
1215         }
1216
1217 }
1218
1219 static
1220 ByteSwap( p, scan)
1221 char    *p;
1222 int     scan;
1223 {
1224         char    w;
1225
1226         switch( scan) {
1227         case 1:
1228                 break;
1229         case 2:
1230                 w = *p;
1231                 *p = *(p + 1);
1232                 *(p + 1) = w;
1233                 break;
1234         case 4:
1235                 w = *p;
1236                 *p = *(p + 3);
1237                 *(p + 3) = w;
1238                 w = *(p + 1);
1239                 *(p + 1) = *(p + 2);
1240                 *(p + 2) = w;
1241                 break;
1242         }
1243 }
1244
1245 static unsigned char _reverse_byte[0x100] = {
1246                         0x00, 0x80, 0x40, 0xc0, 0x20, 0xa0, 0x60, 0xe0,
1247                         0x10, 0x90, 0x50, 0xd0, 0x30, 0xb0, 0x70, 0xf0,
1248                         0x08, 0x88, 0x48, 0xc8, 0x28, 0xa8, 0x68, 0xe8,
1249                         0x18, 0x98, 0x58, 0xd8, 0x38, 0xb8, 0x78, 0xf8,
1250                         0x04, 0x84, 0x44, 0xc4, 0x24, 0xa4, 0x64, 0xe4,
1251                         0x14, 0x94, 0x54, 0xd4, 0x34, 0xb4, 0x74, 0xf4,
1252                         0x0c, 0x8c, 0x4c, 0xcc, 0x2c, 0xac, 0x6c, 0xec,
1253                         0x1c, 0x9c, 0x5c, 0xdc, 0x3c, 0xbc, 0x7c, 0xfc,
1254                         0x02, 0x82, 0x42, 0xc2, 0x22, 0xa2, 0x62, 0xe2,
1255                         0x12, 0x92, 0x52, 0xd2, 0x32, 0xb2, 0x72, 0xf2,
1256                         0x0a, 0x8a, 0x4a, 0xca, 0x2a, 0xaa, 0x6a, 0xea,
1257                         0x1a, 0x9a, 0x5a, 0xda, 0x3a, 0xba, 0x7a, 0xfa,
1258                         0x06, 0x86, 0x46, 0xc6, 0x26, 0xa6, 0x66, 0xe6,
1259                         0x16, 0x96, 0x56, 0xd6, 0x36, 0xb6, 0x76, 0xf6,
1260                         0x0e, 0x8e, 0x4e, 0xce, 0x2e, 0xae, 0x6e, 0xee,
1261                         0x1e, 0x9e, 0x5e, 0xde, 0x3e, 0xbe, 0x7e, 0xfe,
1262                         0x01, 0x81, 0x41, 0xc1, 0x21, 0xa1, 0x61, 0xe1,
1263                         0x11, 0x91, 0x51, 0xd1, 0x31, 0xb1, 0x71, 0xf1,
1264                         0x09, 0x89, 0x49, 0xc9, 0x29, 0xa9, 0x69, 0xe9,
1265                         0x19, 0x99, 0x59, 0xd9, 0x39, 0xb9, 0x79, 0xf9,
1266                         0x05, 0x85, 0x45, 0xc5, 0x25, 0xa5, 0x65, 0xe5,
1267                         0x15, 0x95, 0x55, 0xd5, 0x35, 0xb5, 0x75, 0xf5,
1268                         0x0d, 0x8d, 0x4d, 0xcd, 0x2d, 0xad, 0x6d, 0xed,
1269                         0x1d, 0x9d, 0x5d, 0xdd, 0x3d, 0xbd, 0x7d, 0xfd,
1270                         0x03, 0x83, 0x43, 0xc3, 0x23, 0xa3, 0x63, 0xe3,
1271                         0x13, 0x93, 0x53, 0xd3, 0x33, 0xb3, 0x73, 0xf3,
1272                         0x0b, 0x8b, 0x4b, 0xcb, 0x2b, 0xab, 0x6b, 0xeb,
1273                         0x1b, 0x9b, 0x5b, 0xdb, 0x3b, 0xbb, 0x7b, 0xfb,
1274                         0x07, 0x87, 0x47, 0xc7, 0x27, 0xa7, 0x67, 0xe7,
1275                         0x17, 0x97, 0x57, 0xd7, 0x37, 0xb7, 0x77, 0xf7,
1276                         0x0f, 0x8f, 0x4f, 0xcf, 0x2f, 0xaf, 0x6f, 0xef,
1277                         0x1f, 0x9f, 0x5f, 0xdf, 0x3f, 0xbf, 0x7f, 0xff
1278 };
1279
1280 static  void
1281 BitOrderInvert(buf, nbytes)
1282 register unsigned char *buf;
1283 register int nbytes;
1284 {
1285         register unsigned char *rev = _reverse_byte;
1286
1287         for (; --nbytes >= 0; buf++)
1288                 *buf = rev[*buf];
1289 }
1290
1291 static
1292 invertBits( src, format, width, height, dest)
1293 char    *src;
1294 CARD32  format;
1295 int     width, height;
1296 char    *dest;
1297 {
1298         int     bit, byte, glyph, scan;
1299         int     src_bytewidth, dest_bytewidth;
1300         char    work[8];
1301         int     i, j;
1302
1303         bit = PCF_BIT_ORDER( format);
1304         byte = PCF_BYTE_ORDER( format);
1305         glyph = PCF_GLYPH_PAD( format);
1306         scan = PCF_SCAN_UNIT( format);
1307
1308         src_bytewidth = (( width + ( 8 * glyph ) - 1)/( 8 * glyph)) * glyph;
1309         dest_bytewidth = ( width + 7) /8;
1310
1311         for ( i = 0; i < height; i++, src += src_bytewidth,
1312             dest += dest_bytewidth) {
1313                 for ( j = 0; j < src_bytewidth; j += scan) {
1314                         memcpy( work, src + j, scan);
1315                         if ( bit == LSBFirst)
1316                                 BitOrderInvert( (unsigned char *)work, scan);
1317                         if ( byte == LSBFirst)
1318                                 ByteSwap( work, scan);
1319                         if (( j + scan) >= dest_bytewidth) {
1320                                 memcpy( dest + j, work, dest_bytewidth - j);
1321                                 break;
1322                         }
1323                         memcpy( dest + j, work, scan);
1324                 }
1325         }
1326
1327 }
1328
1329 static  void
1330 pCHARS_pcf (pcf, fix)
1331 PcfTmp  *pcf;
1332 int     fix ;
1333 {
1334         char    *bmp_ptn;
1335         char    *bitmap;
1336         int     ptn_width, ptn_height;
1337         int     bmp_width, bmp_height;
1338         int     cpy_height;
1339         int     row, col;
1340         int     row_width;
1341         int     encoding;
1342         int     encodingOffset;
1343         int     nencoding;
1344         int     bmp_adj, ptn_adj;
1345         int     adj_hi;
1346         int     width_bytes;
1347         INT16   bl, br, ba, bd, bdw ;
1348         unsigned char   cl, cr, ca, cd, cdw ;
1349         unsigned char   *comp ;
1350         int     bbw, bbh, bbx, bby, dwidth ;
1351
1352         fprintf(stdout,"CHARS %d\n",pcf->nbitmaps);
1353
1354         row_width = pcf->info.lastCol - pcf->info.firstCol + 1;
1355         nencoding = row_width * (pcf->info.lastRow - pcf->info.firstRow + 1);
1356
1357         if( fix == TRUE ) {
1358             bmp_width = pcf->info.maxbounds.metrics.leftSideBearing 
1359                     + pcf->info.maxbounds.metrics.rightSideBearing ;
1360             bmp_height = pcf->info.fontAscent + pcf->info.fontDescent ;
1361             ptn_width  = bmp_width ;
1362             ptn_height = pcf->info.maxbounds.metrics.ascent +
1363                         pcf->info.maxbounds.metrics.descent;
1364
1365             if (!(bmp_ptn = make_toptn( ptn_width, ptn_height)))
1366                     return;
1367
1368             if ( ( adj_hi = pcf->info.fontAscent - pcf->info.maxbounds.metrics.ascent ) > 0) {
1369                     width_bytes =  8 * PCF_GLYPH_PAD( pcf->bmp_fmt);
1370                     width_bytes = (( width_bytes + bmp_width - 1)/width_bytes) * PCF_GLYPH_PAD( pcf->bmp_fmt);
1371                     bmp_adj = width_bytes * adj_hi;
1372                     ptn_adj = 0;
1373                     if (( cpy_height = bmp_height - adj_hi) > ptn_height)
1374                             cpy_height = ptn_height ;
1375             } else if ( adj_hi < 0) {
1376                     adj_hi *= -1;
1377                     width_bytes = ( ptn_width + 7) / 8;
1378                     bmp_adj = 0;
1379                     ptn_adj = width_bytes * adj_hi;
1380                     if (( cpy_height = ptn_height - adj_hi) > bmp_height)
1381                             cpy_height = bmp_height ;
1382             } else {
1383                     bmp_adj = 0;
1384                     ptn_adj = 0;
1385                     cpy_height = ptn_height ;
1386             }
1387         }
1388
1389
1390         for ( encoding = 0; encoding < nencoding; encoding++) {
1391                 if(fix == TRUE) memset( bmp_ptn, '\0', (ptn_width + 7)/8 * ptn_height);
1392                 encodingOffset = getINT16( (unsigned char *)(pcf->encodingOffsets + encoding), pcf->enc_fmt);
1393                 if (encodingOffset == 0xFFFF) continue;
1394
1395                 row = pcf->info.firstRow + encoding / row_width;
1396                 col = pcf->info.firstCol + encoding % row_width;
1397
1398                 fprintf(stdout,"STARTCHAR %s\n",pcf->glyph_name + 
1399                    getINT32( (unsigned char*)&pcf->glyph_offset[encodingOffset],
1400                    pcf->glyph_fmt) );
1401                 fprintf(stdout,"ENCODING %d\n",(row << 8) + col);
1402
1403                 fprintf( stdout,"SWIDTH %d 0\n", getINT32( (unsigned char*)(pcf->swidth + encodingOffset), pcf->swd_fmt) );
1404
1405                 if( pcf->compress ){
1406                     comp = (unsigned char*)pcf->metrics + 
1407                                 encodingOffset * SIZEOF_COMPRESSED_METRIC ;
1408                     cl  = getINT8( comp ) ;
1409                     cr  = getINT8( comp ) ;
1410                     cdw = getINT8( comp ) ;
1411                     ca  = getINT8( comp ) ;
1412                     cd  = getINT8( comp ) ;
1413
1414                     dwidth = (int)(cdw - 0x80) ;
1415                     bbw = (int)((cr - 0x80) - (cl - 0x80)) ;
1416                     bbh = (int)((ca - 0x80) + (cd - 0x80)) ;
1417                     bbx = (int)(cl - 0x80) ;
1418                     bby = (int)( -(cd - 0x80) ) ;
1419                 }else{
1420                     bl = getINT16( (unsigned char *)&pcf->metrics[encodingOffset].leftSideBearing, pcf->mtr_fmt ) ;
1421                     br = getINT16( (unsigned char *)&pcf->metrics[encodingOffset].rightSideBearing, pcf->mtr_fmt ) ;
1422                     bdw = getINT16( (unsigned char *)&pcf->metrics[encodingOffset].characterWidth, pcf->mtr_fmt ) ;
1423                     ba = getINT16( (unsigned char *)&pcf->metrics[encodingOffset].ascent, pcf->mtr_fmt ) ;
1424                     bd = getINT16( (unsigned char *)&pcf->metrics[encodingOffset].descent, pcf->mtr_fmt ) ;
1425                     dwidth = bdw ;
1426                     bbw = br-bl ;
1427                     bbh = ba+bd ;
1428                     bbx = bl ;
1429                     bby = -bd ;
1430                 }
1431                 fprintf( stdout,"DWIDTH %d 0\n", dwidth ) ;
1432                 fprintf( stdout,"BBX %d %d %d %d\nBITMAP\n", bbw, bbh, bbx, bby ) ;
1433
1434                 if( fix == FALSE ) {
1435                     bmp_width = pcf->info.maxbounds.metrics.leftSideBearing 
1436                             + pcf->info.maxbounds.metrics.rightSideBearing ;
1437                     bmp_height = pcf->info.fontAscent + pcf->info.fontDescent ;
1438                     ptn_width  = bbw ;
1439                     ptn_height = bbh ;
1440
1441                     if (!(bmp_ptn = make_toptn( ptn_width, ptn_height)))
1442                             return;
1443
1444                     if ( ( adj_hi = pcf->info.fontAscent - pcf->info.maxbounds.metrics.ascent ) > 0) {
1445                         width_bytes =  8 * PCF_GLYPH_PAD( pcf->bmp_fmt);
1446                         width_bytes = (( width_bytes + bmp_width - 1)/width_bytes) * PCF_GLYPH_PAD( pcf->bmp_fmt);
1447                         bmp_adj = width_bytes * adj_hi;
1448                         ptn_adj = 0;
1449                         if (( cpy_height = bmp_height - adj_hi) > ptn_height)
1450                                 cpy_height = ptn_height ;
1451                     } else if ( adj_hi < 0) {
1452                         adj_hi *= -1;
1453                         width_bytes = ( ptn_width + 7) / 8;
1454                         bmp_adj = 0;
1455                         ptn_adj = width_bytes * adj_hi;
1456                         if (( cpy_height = ptn_height - adj_hi) > bmp_height)
1457                                 cpy_height = bmp_height ;
1458                     } else {
1459                         bmp_adj = 0;
1460                         ptn_adj = 0;
1461                         cpy_height = ptn_height ;
1462                     }
1463                     memset( bmp_ptn, '\0', (ptn_width + 7)/8 * ptn_height);
1464                 }
1465
1466                 bitmap = pcf->bitmaps + getINT32( (unsigned char *)(pcf->offsets + encodingOffset),
1467                     pcf->bmp_fmt);
1468                 invertBits( bitmap + bmp_adj, pcf->bmp_fmt, ptn_width, cpy_height, bmp_ptn + ptn_adj);
1469                 putPtn( (unsigned char *)bmp_ptn, ptn_width, ptn_height );
1470                 fprintf(stdout,"ENDCHAR\n");
1471                 if( fix == FALSE )      free(bmp_ptn);
1472         }
1473         if( fix == TRUE )       free(bmp_ptn);
1474         return;
1475 }
1476
1477 static  char *
1478 make_toptn( width, height)
1479 int     width, height;
1480 {
1481         int     byte_width;
1482
1483         byte_width = (width + 7)/8;
1484
1485         return (char *)malloc( byte_width * height);
1486 }
1487
1488
1489
1490
1491 static  int     
1492 getarg(argc,argv,fname,bitorder,byteorder,scanunit,glyphPad,outLevel,fix)
1493 int  argc;
1494 char *argv[];
1495 char *fname;
1496 int  *bitorder;
1497 int  *byteorder;
1498 int  *scanunit;
1499 int  *glyphPad;
1500 int  *outLevel;
1501 int  *fix;
1502 {
1503         int i;
1504         int already;
1505         char *arg;
1506         char *usage="dtgpftobdf [-H] [-V] [-help]  font_file_name";
1507
1508         *glyphPad = DEFAULTGLPAD;
1509         *bitorder = DEFAULTBITORDER;
1510         *scanunit = DEFAULTSCANUNIT;
1511         *byteorder = DEFAULTBYTEORDER;
1512         *outLevel = FALSE;
1513         *fix = FALSE ;
1514         already = 0 ;
1515
1516         for (i = 1; i < argc; i++ ) {
1517                 arg = argv[i];
1518                 if (*arg == '-') {
1519                         *arg++;
1520                         switch (*arg) {
1521                         case 'p' :
1522                                 *glyphPad = atoi(arg+1) ;
1523                                 if (*glyphPad != 1 &&
1524                                     *glyphPad != 2 &&
1525                                     *glyphPad != 4 &&
1526                                     *glyphPad != 8 ) {
1527                                         USAGE("dtgpftobdf : illegal padding number (1/2/4/8)\n");
1528                                         return  -1;
1529                                 }
1530                                 break;
1531                         case 'H' :
1532                                 *outLevel = TRUE ;
1533                                 break;
1534                         case 'h' :
1535                                 USAGE1("usage: %s\n",usage);
1536                                 return (-1);
1537                         case 'V' :
1538                                 *fix = TRUE ;
1539                                 break;
1540                         default :
1541                                 USAGE1("dtgpftobdf : illegal option -- %s\n",arg);
1542                                 USAGE1("usage: %s\n",usage);
1543                                 return  -1;
1544                         }
1545
1546                 } else {
1547                         if (already == FALSE) {
1548                                 strcpy(fname,arg);
1549                                 already = TRUE;
1550                         } else {
1551                                 USAGE1("dtgpftobdf : extra parameter --- %s\n",arg);
1552                                 USAGE1("usage: %s\n", usage );
1553                                 return  -1;
1554                         }
1555                 }
1556         }
1557         if (already == FALSE) {
1558                 USAGE("dtgpftobdf : require file name\n");
1559                 USAGE1("usage: %s\n",usage);
1560                 return  -1;
1561         }
1562         return  0;
1563 }
1564