Visualization Library 2.0.0-b5

A lightweight C++ OpenGL middleware for 2D/3D graphics

VL     Star     Watch     Fork     Issue

[Download] [Tutorials] [All Classes] [Grouped Classes]
ftmac.c
Go to the documentation of this file.
1 /***************************************************************************/
2 /* */
3 /* ftmac.c */
4 /* */
5 /* Mac FOND support. Written by just@letterror.com. */
6 /* Heavily Fixed by mpsuzuki, George Williams and Sean McBride */
7 /* */
8 /* Copyright 1996-2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008 by */
9 /* Just van Rossum, David Turner, Robert Wilhelm, and Werner Lemberg. */
10 /* */
11 /* This file is part of the FreeType project, and may only be used, */
12 /* modified, and distributed under the terms of the FreeType project */
13 /* license, LICENSE.TXT. By continuing to use, modify, or distribute */
14 /* this file you indicate that you have read the license and */
15 /* understand and accept it fully. */
16 /* */
17 /***************************************************************************/
18 
19 
20  /*
21  Notes
22 
23  Mac suitcase files can (and often do!) contain multiple fonts. To
24  support this I use the face_index argument of FT_(Open|New)_Face()
25  functions, and pretend the suitcase file is a collection.
26 
27  Warning: fbit and NFNT bitmap resources are not supported yet. In old
28  sfnt fonts, bitmap glyph data for each size is stored in each `NFNT'
29  resources instead of the `bdat' table in the sfnt resource. Therefore,
30  face->num_fixed_sizes is set to 0, because bitmap data in `NFNT'
31  resource is unavailable at present.
32 
33  The Mac FOND support works roughly like this:
34 
35  - Check whether the offered stream points to a Mac suitcase file. This
36  is done by checking the file type: it has to be 'FFIL' or 'tfil'. The
37  stream that gets passed to our init_face() routine is a stdio stream,
38  which isn't usable for us, since the FOND resources live in the
39  resource fork. So we just grab the stream->pathname field.
40 
41  - Read the FOND resource into memory, then check whether there is a
42  TrueType font and/or(!) a Type 1 font available.
43 
44  - If there is a Type 1 font available (as a separate `LWFN' file), read
45  its data into memory, massage it slightly so it becomes PFB data, wrap
46  it into a memory stream, load the Type 1 driver and delegate the rest
47  of the work to it by calling FT_Open_Face(). (XXX TODO: after this
48  has been done, the kerning data from the FOND resource should be
49  appended to the face: On the Mac there are usually no AFM files
50  available. However, this is tricky since we need to map Mac char
51  codes to ps glyph names to glyph ID's...)
52 
53  - If there is a TrueType font (an `sfnt' resource), read it into memory,
54  wrap it into a memory stream, load the TrueType driver and delegate
55  the rest of the work to it, by calling FT_Open_Face().
56 
57  - Some suitcase fonts (notably Onyx) might point the `LWFN' file to
58  itself, even though it doesn't contains `POST' resources. To handle
59  this special case without opening the file an extra time, we just
60  ignore errors from the `LWFN' and fallback to the `sfnt' if both are
61  available.
62  */
63 
64 
65 #include <ft2build.h>
66 #include FT_FREETYPE_H
67 #include FT_TRUETYPE_TAGS_H
68 #include FT_INTERNAL_STREAM_H
69 #include "ftbase.h"
70 
71 #if defined( __GNUC__ ) || defined( __IBMC__ )
72  /* This is for Mac OS X. Without redefinition, OS_INLINE */
73  /* expands to `static inline' which doesn't survive the */
74  /* -ansi compilation flag of GCC. */
75 #if !HAVE_ANSI_OS_INLINE
76 #undef OS_INLINE
77 #define OS_INLINE static __inline__
78 #endif
79 #include <CoreServices/CoreServices.h>
80 #include <ApplicationServices/ApplicationServices.h>
81 #include <sys/syslimits.h> /* PATH_MAX */
82 #else
83 #include <Resources.h>
84 #include <Fonts.h>
85 #include <Endian.h>
86 #include <Errors.h>
87 #include <Files.h>
88 #include <TextUtils.h>
89 #endif
90 
91 #ifndef PATH_MAX
92 #define PATH_MAX 1024 /* same with Mac OS X's syslimits.h */
93 #endif
94 
95 #if defined( __MWERKS__ ) && !TARGET_RT_MAC_MACHO
96 #include <FSp_fopen.h>
97 #endif
98 
99 #define FT_DEPRECATED_ATTRIBUTE
100 
101 #include FT_MAC_H
102 
103  /* undefine blocking-macros in ftmac.h */
104 #undef FT_GetFile_From_Mac_Name
105 #undef FT_GetFile_From_Mac_ATS_Name
106 #undef FT_New_Face_From_FOND
107 #undef FT_New_Face_From_FSSpec
108 #undef FT_New_Face_From_FSRef
109 
110 
111  /* FSSpec functions are deprecated since Mac OS X 10.4 */
112 #ifndef HAVE_FSSPEC
113 #if TARGET_API_MAC_OS8 || TARGET_API_MAC_CARBON
114 #define HAVE_FSSPEC 1
115 #else
116 #define HAVE_FSSPEC 0
117 #endif
118 #endif
119 
120  /* most FSRef functions were introduced since Mac OS 9 */
121 #ifndef HAVE_FSREF
122 #if TARGET_API_MAC_OSX
123 #define HAVE_FSREF 1
124 #else
125 #define HAVE_FSREF 0
126 #endif
127 #endif
128 
129  /* QuickDraw is deprecated since Mac OS X 10.4 */
130 #ifndef HAVE_QUICKDRAW_CARBON
131 #if TARGET_API_MAC_OS8 || TARGET_API_MAC_CARBON
132 #define HAVE_QUICKDRAW_CARBON 1
133 #else
134 #define HAVE_QUICKDRAW_CARBON 0
135 #endif
136 #endif
137 
138  /* AppleTypeService is available since Mac OS X */
139 #ifndef HAVE_ATS
140 #if TARGET_API_MAC_OSX
141 #define HAVE_ATS 1
142 #ifndef kATSOptionFlagsUnRestrictedScope /* since Mac OS X 10.1 */
143 #define kATSOptionFlagsUnRestrictedScope kATSOptionFlagsDefault
144 #endif
145 #else
146 #define HAVE_ATS 0
147 #endif
148 #endif
149 
150  /* `configure' checks the availability of `ResourceIndex' strictly */
151  /* and sets HAVE_TYPE_RESOURCE_INDEX to 1 or 0 always. If it is */
152  /* not set (e.g., a build without `configure'), the availability */
153  /* is guessed from the SDK version. */
154 #ifndef HAVE_TYPE_RESOURCE_INDEX
155 #if !defined( MAC_OS_X_VERSION_10_5 ) || \
156  ( MAC_OS_X_VERSION_MAX_ALLOWED < MAC_OS_X_VERSION_10_5 )
157 #define HAVE_TYPE_RESOURCE_INDEX 0
158 #else
159 #define HAVE_TYPE_RESOURCE_INDEX 1
160 #endif
161 #endif /* !HAVE_TYPE_RESOURCE_INDEX */
162 
163 #if ( HAVE_TYPE_RESOURCE_INDEX == 0 )
164 typedef short ResourceIndex;
165 #endif
166 
167  /* Set PREFER_LWFN to 1 if LWFN (Type 1) is preferred over
168  TrueType in case *both* are available (this is not common,
169  but it *is* possible). */
170 #ifndef PREFER_LWFN
171 #define PREFER_LWFN 1
172 #endif
173 
174 #ifdef FT_MACINTOSH
175 
176 #if !HAVE_QUICKDRAW_CARBON /* QuickDraw is deprecated since Mac OS X 10.4 */
177 
179  FT_GetFile_From_Mac_Name( const char* fontName,
180  FSSpec* pathSpec,
181  FT_Long* face_index )
182  {
183  FT_UNUSED( fontName );
184  FT_UNUSED( pathSpec );
185  FT_UNUSED( face_index );
186 
187  return FT_Err_Unimplemented_Feature;
188  }
189 
190 #else
191 
193  FT_GetFile_From_Mac_Name( const char* fontName,
194  FSSpec* pathSpec,
195  FT_Long* face_index )
196  {
197  OptionBits options = kFMUseGlobalScopeOption;
198 
199  FMFontFamilyIterator famIter;
200  OSStatus status = FMCreateFontFamilyIterator( NULL, NULL,
201  options,
202  &famIter );
203  FMFont the_font = 0;
204  FMFontFamily family = 0;
205 
206 
207  *face_index = 0;
208  while ( status == 0 && !the_font )
209  {
210  status = FMGetNextFontFamily( &famIter, &family );
211  if ( status == 0 )
212  {
213  int stat2;
214  FMFontFamilyInstanceIterator instIter;
215  Str255 famNameStr;
216  char famName[256];
217 
218 
219  /* get the family name */
220  FMGetFontFamilyName( family, famNameStr );
221  CopyPascalStringToC( famNameStr, famName );
222 
223  /* iterate through the styles */
224  FMCreateFontFamilyInstanceIterator( family, &instIter );
225 
226  *face_index = 0;
227  stat2 = 0;
228 
229  while ( stat2 == 0 && !the_font )
230  {
231  FMFontStyle style;
232  FMFontSize size;
233  FMFont font;
234 
235 
236  stat2 = FMGetNextFontFamilyInstance( &instIter, &font,
237  &style, &size );
238  if ( stat2 == 0 && size == 0 )
239  {
240  char fullName[256];
241 
242 
243  /* build up a complete face name */
244  ft_strcpy( fullName, famName );
245  if ( style & bold )
246  ft_strcat( fullName, " Bold" );
247  if ( style & italic )
248  ft_strcat( fullName, " Italic" );
249 
250  /* compare with the name we are looking for */
251  if ( ft_strcmp( fullName, fontName ) == 0 )
252  {
253  /* found it! */
254  the_font = font;
255  }
256  else
257  ++(*face_index);
258  }
259  }
260 
261  FMDisposeFontFamilyInstanceIterator( &instIter );
262  }
263  }
264 
265  FMDisposeFontFamilyIterator( &famIter );
266 
267  if ( the_font )
268  {
269  FMGetFontContainer( the_font, pathSpec );
270  return FT_Err_Ok;
271  }
272  else
273  return FT_Err_Unknown_File_Format;
274  }
275 
276 #endif /* HAVE_QUICKDRAW_CARBON */
277 
278 
279 #if HAVE_ATS
280 
281  /* Private function. */
282  /* The FSSpec type has been discouraged for a long time, */
283  /* unfortunately an FSRef replacement API for */
284  /* ATSFontGetFileSpecification() is only available in */
285  /* Mac OS X 10.5 and later. */
286  static OSStatus
287  FT_ATSFontGetFileReference( ATSFontRef ats_font_id,
288  FSRef* ats_font_ref )
289  {
290  OSStatus err;
291 
292 #if !defined( MAC_OS_X_VERSION_10_5 ) || \
293  MAC_OS_X_VERSION_MIN_REQUIRED < MAC_OS_X_VERSION_10_5
294  FSSpec spec;
295 
296 
297  err = ATSFontGetFileSpecification( ats_font_id, &spec );
298  if ( noErr == err )
299  err = FSpMakeFSRef( &spec, ats_font_ref );
300 #else
301  err = ATSFontGetFileReference( ats_font_id, ats_font_ref );
302 #endif
303 
304  return err;
305  }
306 
307 
308  static FT_Error
309  FT_GetFileRef_From_Mac_ATS_Name( const char* fontName,
310  FSRef* ats_font_ref,
311  FT_Long* face_index )
312  {
313  CFStringRef cf_fontName;
314  ATSFontRef ats_font_id;
315 
316 
317  *face_index = 0;
318 
319  cf_fontName = CFStringCreateWithCString( NULL, fontName,
320  kCFStringEncodingMacRoman );
321  ats_font_id = ATSFontFindFromName( cf_fontName,
323  CFRelease( cf_fontName );
324 
325  if ( ats_font_id == 0 || ats_font_id == 0xFFFFFFFFUL )
326  return FT_Err_Unknown_File_Format;
327 
328  if ( noErr != FT_ATSFontGetFileReference( ats_font_id, ats_font_ref ) )
329  return FT_Err_Unknown_File_Format;
330 
331  /* face_index calculation by searching preceding fontIDs */
332  /* with same FSRef */
333  {
334  ATSFontRef id2 = ats_font_id - 1;
335  FSRef ref2;
336 
337 
338  while ( id2 > 0 )
339  {
340  if ( noErr != FT_ATSFontGetFileReference( id2, &ref2 ) )
341  break;
342  if ( noErr != FSCompareFSRefs( ats_font_ref, &ref2 ) )
343  break;
344 
345  id2--;
346  }
347  *face_index = ats_font_id - ( id2 + 1 );
348  }
349 
350  return FT_Err_Ok;
351  }
352 
353 #endif
354 
355 #if !HAVE_ATS
356 
359  UInt8* path,
360  UInt32 maxPathSize,
361  FT_Long* face_index )
362  {
363  FT_UNUSED( fontName );
364  FT_UNUSED( path );
365  FT_UNUSED( maxPathSize );
366  FT_UNUSED( face_index );
367 
368  return FT_Err_Unimplemented_Feature;
369  }
370 
371 #else
372 
375  UInt8* path,
376  UInt32 maxPathSize,
377  FT_Long* face_index )
378  {
379  FSRef ref;
380  FT_Error err;
381 
382 
383  err = FT_GetFileRef_From_Mac_ATS_Name( fontName, &ref, face_index );
384  if ( FT_Err_Ok != err )
385  return err;
386 
387  if ( noErr != FSRefMakePath( &ref, path, maxPathSize ) )
388  return FT_Err_Unknown_File_Format;
389 
390  return FT_Err_Ok;
391  }
392 
393 #endif /* HAVE_ATS */
394 
395 
396 #if !HAVE_FSSPEC || !HAVE_ATS
397 
400  FSSpec* pathSpec,
401  FT_Long* face_index )
402  {
403  FT_UNUSED( fontName );
404  FT_UNUSED( pathSpec );
405  FT_UNUSED( face_index );
406 
407  return FT_Err_Unimplemented_Feature;
408  }
409 
410 #else
411 
412  /* This function is deprecated because FSSpec is deprecated in Mac OS X. */
415  FSSpec* pathSpec,
416  FT_Long* face_index )
417  {
418  FSRef ref;
419  FT_Error err;
420 
421 
422  err = FT_GetFileRef_From_Mac_ATS_Name( fontName, &ref, face_index );
423  if ( FT_Err_Ok != err )
424  return err;
425 
426  if ( noErr != FSGetCatalogInfo( &ref, kFSCatInfoNone, NULL, NULL,
427  pathSpec, NULL ) )
428  return FT_Err_Unknown_File_Format;
429 
430  return FT_Err_Ok;
431  }
432 
433 #endif
434 
435 
436 #if defined( __MWERKS__ ) && !TARGET_RT_MAC_MACHO
437 
438 #define STREAM_FILE( stream ) ( (FT_FILE*)stream->descriptor.pointer )
439 
440 
441  FT_CALLBACK_DEF( void )
442  ft_FSp_stream_close( FT_Stream stream )
443  {
444  ft_fclose( STREAM_FILE( stream ) );
445 
446  stream->descriptor.pointer = NULL;
447  stream->size = 0;
448  stream->base = 0;
449  }
450 
451 
452  FT_CALLBACK_DEF( unsigned long )
453  ft_FSp_stream_io( FT_Stream stream,
454  unsigned long offset,
455  unsigned char* buffer,
456  unsigned long count )
457  {
458  FT_FILE* file;
459 
460 
461  file = STREAM_FILE( stream );
462 
463  ft_fseek( file, offset, SEEK_SET );
464 
465  return (unsigned long)ft_fread( buffer, 1, count, file );
466  }
467 
468 #endif /* __MWERKS__ && !TARGET_RT_MAC_MACHO */
469 
470 
471 #if HAVE_FSSPEC && !HAVE_FSREF
472 
473  /* isDirectory is a dummy to synchronize API with FSPathMakeRef() */
474  static OSErr
475  FT_FSPathMakeSpec( const UInt8* pathname,
476  FSSpec* spec_p,
477  Boolean isDirectory )
478  {
479  const char *p, *q;
480  short vRefNum;
481  long dirID;
482  Str255 nodeName;
483  OSErr err;
484  FT_UNUSED( isDirectory );
485 
486 
487  p = q = (const char *)pathname;
488  dirID = 0;
489  vRefNum = 0;
490 
491  while ( 1 )
492  {
493  int len = ft_strlen( p );
494 
495 
496  if ( len > 255 )
497  len = 255;
498 
499  q = p + len;
500 
501  if ( q == p )
502  return 0;
503 
504  if ( 255 < ft_strlen( (char *)pathname ) )
505  {
506  while ( p < q && *q != ':' )
507  q--;
508  }
509 
510  if ( p < q )
511  *(char *)nodeName = q - p;
512  else if ( ft_strlen( p ) < 256 )
513  *(char *)nodeName = ft_strlen( p );
514  else
515  return errFSNameTooLong;
516 
517  ft_strncpy( (char *)nodeName + 1, (char *)p, *(char *)nodeName );
518  err = FSMakeFSSpec( vRefNum, dirID, nodeName, spec_p );
519  if ( err || '\0' == *q )
520  return err;
521 
522  vRefNum = spec_p->vRefNum;
523  dirID = spec_p->parID;
524 
525  p = q;
526  }
527  }
528 
529 
530  static OSErr
531  FT_FSpMakePath( const FSSpec* spec_p,
532  UInt8* path,
533  UInt32 maxPathSize )
534  {
535  OSErr err;
536  FSSpec spec = *spec_p;
537  short vRefNum;
538  long dirID;
539  Str255 parDir_name;
540 
541 
542  FT_MEM_SET( path, 0, maxPathSize );
543  while ( 1 )
544  {
545  int child_namelen = ft_strlen( (char *)path );
546  unsigned char node_namelen = spec.name[0];
547  unsigned char* node_name = spec.name + 1;
548 
549 
550  if ( node_namelen + child_namelen > maxPathSize )
551  return errFSNameTooLong;
552 
553  FT_MEM_MOVE( path + node_namelen + 1, path, child_namelen );
554  FT_MEM_COPY( path, node_name, node_namelen );
555  if ( child_namelen > 0 )
556  path[node_namelen] = ':';
557 
558  vRefNum = spec.vRefNum;
559  dirID = spec.parID;
560  parDir_name[0] = '\0';
561  err = FSMakeFSSpec( vRefNum, dirID, parDir_name, &spec );
562  if ( noErr != err || dirID == spec.parID )
563  break;
564  }
565  return noErr;
566  }
567 
568 #endif /* HAVE_FSSPEC && !HAVE_FSREF */
569 
570 
571  static OSErr
572  FT_FSPathMakeRes( const UInt8* pathname,
573  ResFileRefNum* res )
574  {
575 
576 #if HAVE_FSREF
577 
578  OSErr err;
579  FSRef ref;
580 
581 
582  if ( noErr != FSPathMakeRef( pathname, &ref, FALSE ) )
583  return FT_Err_Cannot_Open_Resource;
584 
585  /* at present, no support for dfont format */
586  err = FSOpenResourceFile( &ref, 0, NULL, fsRdPerm, res );
587  if ( noErr == err )
588  return err;
589 
590  /* fallback to original resource-fork font */
591  *res = FSOpenResFile( &ref, fsRdPerm );
592  err = ResError();
593 
594 #else
595 
596  OSErr err;
597  FSSpec spec;
598 
599 
600  if ( noErr != FT_FSPathMakeSpec( pathname, &spec, FALSE ) )
601  return FT_Err_Cannot_Open_Resource;
602 
603  /* at present, no support for dfont format without FSRef */
604  /* (see above), try original resource-fork font */
605  *res = FSpOpenResFile( &spec, fsRdPerm );
606  err = ResError();
607 
608 #endif /* HAVE_FSREF */
609 
610  return err;
611  }
612 
613 
614  /* Return the file type for given pathname */
615  static OSType
616  get_file_type_from_path( const UInt8* pathname )
617  {
618 
619 #if HAVE_FSREF
620 
621  FSRef ref;
622  FSCatalogInfo info;
623 
624 
625  if ( noErr != FSPathMakeRef( pathname, &ref, FALSE ) )
626  return ( OSType ) 0;
627 
628  if ( noErr != FSGetCatalogInfo( &ref, kFSCatInfoFinderInfo, &info,
629  NULL, NULL, NULL ) )
630  return ( OSType ) 0;
631 
632  return ((FInfo *)(info.finderInfo))->fdType;
633 
634 #else
635 
636  FSSpec spec;
637  FInfo finfo;
638 
639 
640  if ( noErr != FT_FSPathMakeSpec( pathname, &spec, FALSE ) )
641  return ( OSType ) 0;
642 
643  if ( noErr != FSpGetFInfo( &spec, &finfo ) )
644  return ( OSType ) 0;
645 
646  return finfo.fdType;
647 
648 #endif /* HAVE_FSREF */
649 
650  }
651 
652 
653  /* Given a PostScript font name, create the Macintosh LWFN file name. */
654  static void
655  create_lwfn_name( char* ps_name,
656  Str255 lwfn_file_name )
657  {
658  int max = 5, count = 0;
659  FT_Byte* p = lwfn_file_name;
660  FT_Byte* q = (FT_Byte*)ps_name;
661 
662 
663  lwfn_file_name[0] = 0;
664 
665  while ( *q )
666  {
667  if ( ft_isupper( *q ) )
668  {
669  if ( count )
670  max = 3;
671  count = 0;
672  }
673  if ( count < max && ( ft_isalnum( *q ) || *q == '_' ) )
674  {
675  *++p = *q;
676  lwfn_file_name[0]++;
677  count++;
678  }
679  q++;
680  }
681  }
682 
683 
684  static short
685  count_faces_sfnt( char* fond_data )
686  {
687  /* The count is 1 greater than the value in the FOND. */
688  /* Isn't that cute? :-) */
689 
690  return EndianS16_BtoN( *( (short*)( fond_data +
691  sizeof ( FamRec ) ) ) ) + 1;
692  }
693 
694 
695  static short
696  count_faces_scalable( char* fond_data )
697  {
698  AsscEntry* assoc;
699  FamRec* fond;
700  short i, face, face_all;
701 
702 
703  fond = (FamRec*)fond_data;
704  face_all = EndianS16_BtoN( *( (short *)( fond_data +
705  sizeof ( FamRec ) ) ) ) + 1;
706  assoc = (AsscEntry*)( fond_data + sizeof ( FamRec ) + 2 );
707  face = 0;
708 
709  for ( i = 0; i < face_all; i++ )
710  {
711  if ( 0 == EndianS16_BtoN( assoc[i].fontSize ) )
712  face++;
713  }
714  return face;
715  }
716 
717 
718  /* Look inside the FOND data, answer whether there should be an SFNT
719  resource, and answer the name of a possible LWFN Type 1 file.
720 
721  Thanks to Paul Miller (paulm@profoundeffects.com) for the fix
722  to load a face OTHER than the first one in the FOND!
723  */
724 
725  static void
726  parse_fond( char* fond_data,
727  short* have_sfnt,
728  ResID* sfnt_id,
729  Str255 lwfn_file_name,
730  short face_index )
731  {
732  AsscEntry* assoc;
733  AsscEntry* base_assoc;
734  FamRec* fond;
735 
736 
737  *sfnt_id = 0;
738  *have_sfnt = 0;
739  lwfn_file_name[0] = 0;
740 
741  fond = (FamRec*)fond_data;
742  assoc = (AsscEntry*)( fond_data + sizeof ( FamRec ) + 2 );
743  base_assoc = assoc;
744 
745  /* the maximum faces in a FOND is 48, size of StyleTable.indexes[] */
746  if ( 47 < face_index )
747  return;
748 
749  /* Let's do a little range checking before we get too excited here */
750  if ( face_index < count_faces_sfnt( fond_data ) )
751  {
752  assoc += face_index; /* add on the face_index! */
753 
754  /* if the face at this index is not scalable,
755  fall back to the first one (old behavior) */
756  if ( EndianS16_BtoN( assoc->fontSize ) == 0 )
757  {
758  *have_sfnt = 1;
759  *sfnt_id = EndianS16_BtoN( assoc->fontID );
760  }
761  else if ( base_assoc->fontSize == 0 )
762  {
763  *have_sfnt = 1;
764  *sfnt_id = EndianS16_BtoN( base_assoc->fontID );
765  }
766  }
767 
768  if ( EndianS32_BtoN( fond->ffStylOff ) )
769  {
770  unsigned char* p = (unsigned char*)fond_data;
771  StyleTable* style;
772  unsigned short string_count;
773  char ps_name[256];
774  unsigned char* names[64];
775  int i;
776 
777 
778  p += EndianS32_BtoN( fond->ffStylOff );
779  style = (StyleTable*)p;
780  p += sizeof ( StyleTable );
781  string_count = EndianS16_BtoN( *(short*)(p) );
782  p += sizeof ( short );
783 
784  for ( i = 0; i < string_count && i < 64; i++ )
785  {
786  names[i] = p;
787  p += names[i][0];
788  p++;
789  }
790 
791  {
792  size_t ps_name_len = (size_t)names[0][0];
793 
794 
795  if ( ps_name_len != 0 )
796  {
797  ft_memcpy(ps_name, names[0] + 1, ps_name_len);
798  ps_name[ps_name_len] = 0;
799  }
800  if ( style->indexes[face_index] > 1 &&
801  style->indexes[face_index] <= FT_MIN( string_count, 64 ) )
802  {
803  unsigned char* suffixes = names[style->indexes[face_index] - 1];
804 
805 
806  for ( i = 1; i <= suffixes[0]; i++ )
807  {
808  unsigned char* s;
809  size_t j = suffixes[i] - 1;
810 
811 
812  if ( j < string_count && ( s = names[j] ) != NULL )
813  {
814  size_t s_len = (size_t)s[0];
815 
816 
817  if ( s_len != 0 && ps_name_len + s_len < sizeof ( ps_name ) )
818  {
819  ft_memcpy( ps_name + ps_name_len, s + 1, s_len );
820  ps_name_len += s_len;
821  ps_name[ps_name_len] = 0;
822  }
823  }
824  }
825  }
826  }
827 
828  create_lwfn_name( ps_name, lwfn_file_name );
829  }
830  }
831 
832 
833  static FT_Error
834  lookup_lwfn_by_fond( const UInt8* path_fond,
835  ConstStr255Param base_lwfn,
836  UInt8* path_lwfn,
837  int path_size )
838  {
839 
840 #if HAVE_FSREF
841 
842  FSRef ref, par_ref;
843  int dirname_len;
844 
845 
846  /* Pathname for FSRef can be in various formats: HFS, HFS+, and POSIX. */
847  /* We should not extract parent directory by string manipulation. */
848 
849  if ( noErr != FSPathMakeRef( path_fond, &ref, FALSE ) )
850  return FT_Err_Invalid_Argument;
851 
852  if ( noErr != FSGetCatalogInfo( &ref, kFSCatInfoNone,
853  NULL, NULL, NULL, &par_ref ) )
854  return FT_Err_Invalid_Argument;
855 
856  if ( noErr != FSRefMakePath( &par_ref, path_lwfn, path_size ) )
857  return FT_Err_Invalid_Argument;
858 
859  if ( ft_strlen( (char *)path_lwfn ) + 1 + base_lwfn[0] > path_size )
860  return FT_Err_Invalid_Argument;
861 
862  /* now we have absolute dirname in path_lwfn */
863  if ( path_lwfn[0] == '/' )
864  ft_strcat( (char *)path_lwfn, "/" );
865  else
866  ft_strcat( (char *)path_lwfn, ":" );
867 
868  dirname_len = ft_strlen( (char *)path_lwfn );
869  ft_strcat( (char *)path_lwfn, (char *)base_lwfn + 1 );
870  path_lwfn[dirname_len + base_lwfn[0]] = '\0';
871 
872  if ( noErr != FSPathMakeRef( path_lwfn, &ref, FALSE ) )
873  return FT_Err_Cannot_Open_Resource;
874 
875  if ( noErr != FSGetCatalogInfo( &ref, kFSCatInfoNone,
876  NULL, NULL, NULL, NULL ) )
877  return FT_Err_Cannot_Open_Resource;
878 
879  return FT_Err_Ok;
880 
881 #else
882 
883  int i;
884  FSSpec spec;
885 
886 
887  /* pathname for FSSpec is always HFS format */
888  if ( ft_strlen( (char *)path_fond ) > path_size )
889  return FT_Err_Invalid_Argument;
890 
891  ft_strcpy( (char *)path_lwfn, (char *)path_fond );
892 
893  i = ft_strlen( (char *)path_lwfn ) - 1;
894  while ( i > 0 && ':' != path_lwfn[i] )
895  i--;
896 
897  if ( i + 1 + base_lwfn[0] > path_size )
898  return FT_Err_Invalid_Argument;
899 
900  if ( ':' == path_lwfn[i] )
901  {
902  ft_strcpy( (char *)path_lwfn + i + 1, (char *)base_lwfn + 1 );
903  path_lwfn[i + 1 + base_lwfn[0]] = '\0';
904  }
905  else
906  {
907  ft_strcpy( (char *)path_lwfn, (char *)base_lwfn + 1 );
908  path_lwfn[base_lwfn[0]] = '\0';
909  }
910 
911  if ( noErr != FT_FSPathMakeSpec( path_lwfn, &spec, FALSE ) )
912  return FT_Err_Cannot_Open_Resource;
913 
914  return FT_Err_Ok;
915 
916 #endif /* HAVE_FSREF */
917 
918  }
919 
920 
921  static short
922  count_faces( Handle fond,
923  const UInt8* pathname )
924  {
925  ResID sfnt_id;
926  short have_sfnt, have_lwfn;
927  Str255 lwfn_file_name;
928  UInt8 buff[PATH_MAX];
929  FT_Error err;
930  short num_faces;
931 
932 
933  have_sfnt = have_lwfn = 0;
934 
935  HLock( fond );
936  parse_fond( *fond, &have_sfnt, &sfnt_id, lwfn_file_name, 0 );
937 
938  if ( lwfn_file_name[0] )
939  {
940  err = lookup_lwfn_by_fond( pathname, lwfn_file_name,
941  buff, sizeof ( buff ) );
942  if ( FT_Err_Ok == err )
943  have_lwfn = 1;
944  }
945 
946  if ( have_lwfn && ( !have_sfnt || PREFER_LWFN ) )
947  num_faces = 1;
948  else
949  num_faces = count_faces_scalable( *fond );
950 
951  HUnlock( fond );
952  return num_faces;
953  }
954 
955 
956  /* Read Type 1 data from the POST resources inside the LWFN file,
957  return a PFB buffer. This is somewhat convoluted because the FT2
958  PFB parser wants the ASCII header as one chunk, and the LWFN
959  chunks are often not organized that way, so we glue chunks
960  of the same type together. */
961  static FT_Error
962  read_lwfn( FT_Memory memory,
963  ResFileRefNum res,
964  FT_Byte** pfb_data,
965  FT_ULong* size )
966  {
968  ResID res_id;
969  unsigned char *buffer, *p, *size_p = NULL;
970  FT_ULong total_size = 0;
971  FT_ULong old_total_size = 0;
972  FT_ULong post_size, pfb_chunk_size;
973  Handle post_data;
974  char code, last_code;
975 
976 
977  UseResFile( res );
978 
979  /* First pass: load all POST resources, and determine the size of */
980  /* the output buffer. */
981  res_id = 501;
982  last_code = -1;
983 
984  for (;;)
985  {
986  post_data = Get1Resource( TTAG_POST, res_id++ );
987  if ( post_data == NULL )
988  break; /* we are done */
989 
990  code = (*post_data)[0];
991 
992  if ( code != last_code )
993  {
994  if ( code == 5 )
995  total_size += 2; /* just the end code */
996  else
997  total_size += 6; /* code + 4 bytes chunk length */
998  }
999 
1000  total_size += GetHandleSize( post_data ) - 2;
1001  last_code = code;
1002 
1003  /* detect integer overflows */
1004  if ( total_size < old_total_size )
1005  {
1006  error = FT_Err_Array_Too_Large;
1007  goto Error;
1008  }
1009 
1010  old_total_size = total_size;
1011  }
1012 
1013  if ( FT_ALLOC( buffer, (FT_Long)total_size ) )
1014  goto Error;
1015 
1016  /* Second pass: append all POST data to the buffer, add PFB fields. */
1017  /* Glue all consecutive chunks of the same type together. */
1018  p = buffer;
1019  res_id = 501;
1020  last_code = -1;
1021  pfb_chunk_size = 0;
1022 
1023  for (;;)
1024  {
1025  post_data = Get1Resource( TTAG_POST, res_id++ );
1026  if ( post_data == NULL )
1027  break; /* we are done */
1028 
1029  post_size = (FT_ULong)GetHandleSize( post_data ) - 2;
1030  code = (*post_data)[0];
1031 
1032  if ( code != last_code )
1033  {
1034  if ( last_code != -1 )
1035  {
1036  /* we are done adding a chunk, fill in the size field */
1037  if ( size_p != NULL )
1038  {
1039  *size_p++ = (FT_Byte)( pfb_chunk_size & 0xFF );
1040  *size_p++ = (FT_Byte)( ( pfb_chunk_size >> 8 ) & 0xFF );
1041  *size_p++ = (FT_Byte)( ( pfb_chunk_size >> 16 ) & 0xFF );
1042  *size_p++ = (FT_Byte)( ( pfb_chunk_size >> 24 ) & 0xFF );
1043  }
1044  pfb_chunk_size = 0;
1045  }
1046 
1047  *p++ = 0x80;
1048  if ( code == 5 )
1049  *p++ = 0x03; /* the end */
1050  else if ( code == 2 )
1051  *p++ = 0x02; /* binary segment */
1052  else
1053  *p++ = 0x01; /* ASCII segment */
1054 
1055  if ( code != 5 )
1056  {
1057  size_p = p; /* save for later */
1058  p += 4; /* make space for size field */
1059  }
1060  }
1061 
1062  ft_memcpy( p, *post_data + 2, post_size );
1063  pfb_chunk_size += post_size;
1064  p += post_size;
1065  last_code = code;
1066  }
1067 
1068  *pfb_data = buffer;
1069  *size = total_size;
1070 
1071  Error:
1072  CloseResFile( res );
1073  return error;
1074  }
1075 
1076 
1077  /* Create a new FT_Face from a file spec to an LWFN file. */
1078  static FT_Error
1079  FT_New_Face_From_LWFN( FT_Library library,
1080  const UInt8* pathname,
1081  FT_Long face_index,
1082  FT_Face* aface )
1083  {
1084  FT_Byte* pfb_data;
1085  FT_ULong pfb_size;
1086  FT_Error error;
1087  ResFileRefNum res;
1088 
1089 
1090  if ( noErr != FT_FSPathMakeRes( pathname, &res ) )
1091  return FT_Err_Cannot_Open_Resource;
1092 
1093  pfb_data = NULL;
1094  pfb_size = 0;
1095  error = read_lwfn( library->memory, res, &pfb_data, &pfb_size );
1096  CloseResFile( res ); /* PFB is already loaded, useless anymore */
1097  if ( error )
1098  return error;
1099 
1100  return open_face_from_buffer( library,
1101  pfb_data,
1102  pfb_size,
1103  face_index,
1104  "type1",
1105  aface );
1106  }
1107 
1108 
1109  /* Create a new FT_Face from an SFNT resource, specified by res ID. */
1110  static FT_Error
1111  FT_New_Face_From_SFNT( FT_Library library,
1112  ResID sfnt_id,
1113  FT_Long face_index,
1114  FT_Face* aface )
1115  {
1116  Handle sfnt = NULL;
1117  FT_Byte* sfnt_data;
1118  size_t sfnt_size;
1120  FT_Memory memory = library->memory;
1121  int is_cff, is_sfnt_ps;
1122 
1123 
1124  sfnt = GetResource( TTAG_sfnt, sfnt_id );
1125  if ( sfnt == NULL )
1126  return FT_Err_Invalid_Handle;
1127 
1128  sfnt_size = (FT_ULong)GetHandleSize( sfnt );
1129  if ( FT_ALLOC( sfnt_data, (FT_Long)sfnt_size ) )
1130  {
1131  ReleaseResource( sfnt );
1132  return error;
1133  }
1134 
1135  HLock( sfnt );
1136  ft_memcpy( sfnt_data, *sfnt, sfnt_size );
1137  HUnlock( sfnt );
1138  ReleaseResource( sfnt );
1139 
1140  is_cff = sfnt_size > 4 && !ft_memcmp( sfnt_data, "OTTO", 4 );
1141  is_sfnt_ps = sfnt_size > 4 && !ft_memcmp( sfnt_data, "typ1", 4 );
1142 
1143  if ( is_sfnt_ps )
1144  {
1145  FT_Stream stream;
1146 
1147 
1148  if ( FT_NEW( stream ) )
1149  goto Try_OpenType;
1150 
1151  FT_Stream_OpenMemory( stream, sfnt_data, sfnt_size );
1152  if ( !open_face_PS_from_sfnt_stream( library,
1153  stream,
1154  face_index,
1155  0, NULL,
1156  aface ) )
1157  {
1158  FT_Stream_Close( stream );
1159  FT_FREE( stream );
1160  FT_FREE( sfnt_data );
1161  goto Exit;
1162  }
1163 
1164  FT_FREE( stream );
1165  }
1166  Try_OpenType:
1167  error = open_face_from_buffer( library,
1168  sfnt_data,
1169  sfnt_size,
1170  face_index,
1171  is_cff ? "cff" : "truetype",
1172  aface );
1173  Exit:
1174  return error;
1175  }
1176 
1177 
1178  /* Create a new FT_Face from a file spec to a suitcase file. */
1179  static FT_Error
1180  FT_New_Face_From_Suitcase( FT_Library library,
1181  const UInt8* pathname,
1182  FT_Long face_index,
1183  FT_Face* aface )
1184  {
1185  FT_Error error = FT_Err_Cannot_Open_Resource;
1186  ResFileRefNum res_ref;
1187  ResourceIndex res_index;
1188  Handle fond;
1189  short num_faces_in_res, num_faces_in_fond;
1190 
1191 
1192  if ( noErr != FT_FSPathMakeRes( pathname, &res_ref ) )
1193  return FT_Err_Cannot_Open_Resource;
1194 
1195  UseResFile( res_ref );
1196  if ( ResError() )
1197  return FT_Err_Cannot_Open_Resource;
1198 
1199  num_faces_in_res = 0;
1200  for ( res_index = 1; ; ++res_index )
1201  {
1202  fond = Get1IndResource( TTAG_FOND, res_index );
1203  if ( ResError() )
1204  break;
1205 
1206  num_faces_in_fond = count_faces( fond, pathname );
1207  num_faces_in_res += num_faces_in_fond;
1208 
1209  if ( 0 <= face_index && face_index < num_faces_in_fond && error )
1210  error = FT_New_Face_From_FOND( library, fond, face_index, aface );
1211 
1212  face_index -= num_faces_in_fond;
1213  }
1214 
1215  CloseResFile( res_ref );
1216  if ( FT_Err_Ok == error && NULL != aface )
1217  (*aface)->num_faces = num_faces_in_res;
1218  return error;
1219  }
1220 
1221 
1222  /* documentation is in ftmac.h */
1223 
1226  Handle fond,
1227  FT_Long face_index,
1228  FT_Face* aface )
1229  {
1230  short have_sfnt, have_lwfn = 0;
1231  ResID sfnt_id, fond_id;
1232  OSType fond_type;
1233  Str255 fond_name;
1234  Str255 lwfn_file_name;
1235  UInt8 path_lwfn[PATH_MAX];
1236  OSErr err;
1238 
1239 
1240  GetResInfo( fond, &fond_id, &fond_type, fond_name );
1241  if ( ResError() != noErr || fond_type != TTAG_FOND )
1242  return FT_Err_Invalid_File_Format;
1243 
1244  HLock( fond );
1245  parse_fond( *fond, &have_sfnt, &sfnt_id, lwfn_file_name, face_index );
1246  HUnlock( fond );
1247 
1248  if ( lwfn_file_name[0] )
1249  {
1250  ResFileRefNum res;
1251 
1252 
1253  res = HomeResFile( fond );
1254  if ( noErr != ResError() )
1255  goto found_no_lwfn_file;
1256 
1257 #if HAVE_FSREF
1258 
1259  {
1260  UInt8 path_fond[PATH_MAX];
1261  FSRef ref;
1262 
1263 
1264  err = FSGetForkCBInfo( res, kFSInvalidVolumeRefNum,
1265  NULL, NULL, NULL, &ref, NULL );
1266  if ( noErr != err )
1267  goto found_no_lwfn_file;
1268 
1269  err = FSRefMakePath( &ref, path_fond, sizeof ( path_fond ) );
1270  if ( noErr != err )
1271  goto found_no_lwfn_file;
1272 
1273  error = lookup_lwfn_by_fond( path_fond, lwfn_file_name,
1274  path_lwfn, sizeof ( path_lwfn ) );
1275  if ( FT_Err_Ok == error )
1276  have_lwfn = 1;
1277  }
1278 
1279 #elif HAVE_FSSPEC
1280 
1281  {
1282  UInt8 path_fond[PATH_MAX];
1283  FCBPBRec pb;
1284  Str255 fond_file_name;
1285  FSSpec spec;
1286 
1287 
1288  FT_MEM_SET( &spec, 0, sizeof ( FSSpec ) );
1289  FT_MEM_SET( &pb, 0, sizeof ( FCBPBRec ) );
1290 
1291  pb.ioNamePtr = fond_file_name;
1292  pb.ioVRefNum = 0;
1293  pb.ioRefNum = res;
1294  pb.ioFCBIndx = 0;
1295 
1296  err = PBGetFCBInfoSync( &pb );
1297  if ( noErr != err )
1298  goto found_no_lwfn_file;
1299 
1300  err = FSMakeFSSpec( pb.ioFCBVRefNum, pb.ioFCBParID,
1301  fond_file_name, &spec );
1302  if ( noErr != err )
1303  goto found_no_lwfn_file;
1304 
1305  err = FT_FSpMakePath( &spec, path_fond, sizeof ( path_fond ) );
1306  if ( noErr != err )
1307  goto found_no_lwfn_file;
1308 
1309  error = lookup_lwfn_by_fond( path_fond, lwfn_file_name,
1310  path_lwfn, sizeof ( path_lwfn ) );
1311  if ( FT_Err_Ok == error )
1312  have_lwfn = 1;
1313  }
1314 
1315 #endif /* HAVE_FSREF, HAVE_FSSPEC */
1316 
1317  }
1318 
1319  if ( have_lwfn && ( !have_sfnt || PREFER_LWFN ) )
1320  error = FT_New_Face_From_LWFN( library,
1321  path_lwfn,
1322  face_index,
1323  aface );
1324  else
1325  error = FT_Err_Unknown_File_Format;
1326 
1327  found_no_lwfn_file:
1328  if ( have_sfnt && FT_Err_Ok != error )
1329  error = FT_New_Face_From_SFNT( library,
1330  sfnt_id,
1331  face_index,
1332  aface );
1333 
1334  return error;
1335  }
1336 
1337 
1338  /* Common function to load a new FT_Face from a resource file. */
1339  static FT_Error
1340  FT_New_Face_From_Resource( FT_Library library,
1341  const UInt8* pathname,
1342  FT_Long face_index,
1343  FT_Face* aface )
1344  {
1345  OSType file_type;
1346  FT_Error error;
1347 
1348 
1349  /* LWFN is a (very) specific file format, check for it explicitly */
1350  file_type = get_file_type_from_path( pathname );
1351  if ( file_type == TTAG_LWFN )
1352  return FT_New_Face_From_LWFN( library, pathname, face_index, aface );
1353 
1354  /* Otherwise the file type doesn't matter (there are more than */
1355  /* `FFIL' and `tfil'). Just try opening it as a font suitcase; */
1356  /* if it works, fine. */
1357 
1358  error = FT_New_Face_From_Suitcase( library, pathname, face_index, aface );
1359  if ( error == 0 )
1360  return error;
1361 
1362  /* let it fall through to normal loader (.ttf, .otf, etc.); */
1363  /* we signal this by returning no error and no FT_Face */
1364  *aface = NULL;
1365  return 0;
1366  }
1367 
1368 
1369  /*************************************************************************/
1370  /* */
1371  /* <Function> */
1372  /* FT_New_Face */
1373  /* */
1374  /* <Description> */
1375  /* This is the Mac-specific implementation of FT_New_Face. In */
1376  /* addition to the standard FT_New_Face() functionality, it also */
1377  /* accepts pathnames to Mac suitcase files. For further */
1378  /* documentation see the original FT_New_Face() in freetype.h. */
1379  /* */
1381  FT_New_Face( FT_Library library,
1382  const char* pathname,
1383  FT_Long face_index,
1384  FT_Face* aface )
1385  {
1386  FT_Open_Args args;
1387  FT_Error error;
1388 
1389 
1390  /* test for valid `library' and `aface' delayed to FT_Open_Face() */
1391  if ( !pathname )
1392  return FT_Err_Invalid_Argument;
1393 
1394  error = FT_Err_Ok;
1395  *aface = NULL;
1396 
1397  /* try resourcefork based font: LWFN, FFIL */
1398  error = FT_New_Face_From_Resource( library, (UInt8 *)pathname,
1399  face_index, aface );
1400  if ( error != 0 || *aface != NULL )
1401  return error;
1402 
1403  /* let it fall through to normal loader (.ttf, .otf, etc.) */
1404  args.flags = FT_OPEN_PATHNAME;
1405  args.pathname = (char*)pathname;
1406  return FT_Open_Face( library, &args, face_index, aface );
1407  }
1408 
1409 
1410  /*************************************************************************/
1411  /* */
1412  /* <Function> */
1413  /* FT_New_Face_From_FSRef */
1414  /* */
1415  /* <Description> */
1416  /* FT_New_Face_From_FSRef is identical to FT_New_Face except it */
1417  /* accepts an FSRef instead of a path. */
1418  /* */
1419  /* This function is deprecated because Carbon data types (FSRef) */
1420  /* are not cross-platform, and thus not suitable for the freetype API. */
1423  const FSRef* ref,
1424  FT_Long face_index,
1425  FT_Face* aface )
1426  {
1427 
1428 #if !HAVE_FSREF
1429 
1430  FT_UNUSED( library );
1431  FT_UNUSED( ref );
1432  FT_UNUSED( face_index );
1433  FT_UNUSED( aface );
1434 
1435  return FT_Err_Unimplemented_Feature;
1436 
1437 #else
1438 
1439  FT_Error error;
1440  FT_Open_Args args;
1441  OSErr err;
1442  UInt8 pathname[PATH_MAX];
1443 
1444 
1445  if ( !ref )
1446  return FT_Err_Invalid_Argument;
1447 
1448  err = FSRefMakePath( ref, pathname, sizeof ( pathname ) );
1449  if ( err )
1450  error = FT_Err_Cannot_Open_Resource;
1451 
1452  error = FT_New_Face_From_Resource( library, pathname, face_index, aface );
1453  if ( error != 0 || *aface != NULL )
1454  return error;
1455 
1456  /* fallback to datafork font */
1457  args.flags = FT_OPEN_PATHNAME;
1458  args.pathname = (char*)pathname;
1459  return FT_Open_Face( library, &args, face_index, aface );
1460 
1461 #endif /* HAVE_FSREF */
1462 
1463  }
1464 
1465 
1466  /*************************************************************************/
1467  /* */
1468  /* <Function> */
1469  /* FT_New_Face_From_FSSpec */
1470  /* */
1471  /* <Description> */
1472  /* FT_New_Face_From_FSSpec is identical to FT_New_Face except it */
1473  /* accepts an FSSpec instead of a path. */
1474  /* */
1475  /* This function is deprecated because Carbon data types (FSSpec) */
1476  /* are not cross-platform, and thus not suitable for the freetype API. */
1479  const FSSpec* spec,
1480  FT_Long face_index,
1481  FT_Face* aface )
1482  {
1483 
1484 #if HAVE_FSREF
1485 
1486  FSRef ref;
1487 
1488 
1489  if ( !spec || FSpMakeFSRef( spec, &ref ) != noErr )
1490  return FT_Err_Invalid_Argument;
1491  else
1492  return FT_New_Face_From_FSRef( library, &ref, face_index, aface );
1493 
1494 #elif HAVE_FSSPEC
1495 
1496  FT_Error error;
1497  FT_Open_Args args;
1498  OSErr err;
1499  UInt8 pathname[PATH_MAX];
1500 
1501 
1502  if ( !spec )
1503  return FT_Err_Invalid_Argument;
1504 
1505  err = FT_FSpMakePath( spec, pathname, sizeof ( pathname ) );
1506  if ( err )
1507  error = FT_Err_Cannot_Open_Resource;
1508 
1509  error = FT_New_Face_From_Resource( library, pathname, face_index, aface );
1510  if ( error != 0 || *aface != NULL )
1511  return error;
1512 
1513  /* fallback to datafork font */
1514  args.flags = FT_OPEN_PATHNAME;
1515  args.pathname = (char*)pathname;
1516  return FT_Open_Face( library, &args, face_index, aface );
1517 
1518 #else
1519 
1520  FT_UNUSED( library );
1521  FT_UNUSED( spec );
1522  FT_UNUSED( face_index );
1523  FT_UNUSED( aface );
1524 
1525  return FT_Err_Unimplemented_Feature;
1526 
1527 #endif /* HAVE_FSREF, HAVE_FSSPEC */
1528 
1529  }
1530 
1531 #endif /* FT_MACINTOSH */
1532 
1533 
1534 /* END */
unsigned char * base
Definition: ftsystem.h:323
#define FT_ALLOC(ptr, size)
Definition: ftmemory.h:260
int FT_Error
Definition: fttypes.h:296
GLuint GLuint stream
FT_New_Face_From_FSRef(FT_Library library, const FSRef *ref, FT_Long face_index, FT_Face *aface) FT_DEPRECATED_ATTRIBUTE
signed long FT_Long
Definition: fttypes.h:238
unsigned long FT_ULong
Definition: fttypes.h:249
unsigned long size
Definition: ftsystem.h:324
#define FT_OPEN_PATHNAME
Definition: freetype.h:1741
GLfloat GLfloat p
FT_UInt flags
Definition: freetype.h:1838
#define NULL
Definition: ftobjs.h:61
GLdouble GLdouble GLdouble GLdouble q
FT_GetFilePath_From_Mac_ATS_Name(const char *fontName, UInt8 *path, UInt32 maxPathSize, FT_Long *face_index) FT_DEPRECATED_ATTRIBUTE
FT_String * pathname
Definition: freetype.h:1841
#define ft_fread
Definition: ftstdlib.h:106
#define FT_UNUSED(arg)
Definition: ftconfig.h:76
#define FT_MIN(a, b)
Definition: ftobjs.h:70
#define ft_strcat
Definition: ftstdlib.h:84
#define kATSOptionFlagsUnRestrictedScope
Definition: ftmac.c:109
FT_Library library
Definition: cffdrivr.c:414
return FT_Err_Ok
Definition: ftbbox.c:645
FT_Stream_Close(FT_Stream stream)
Definition: ftstream.c:49
GLuint GLuint * names
FT_BEGIN_HEADER open_face_PS_from_sfnt_stream(FT_Library library, FT_Stream stream, FT_Long face_index, FT_Int num_params, FT_Parameter *params, FT_Face *aface)
png_uint_32 i
Definition: png.h:2640
GLenum GLuint GLint GLenum face
open_face_from_buffer(FT_Library library, FT_Byte *base, FT_ULong size, FT_Long face_index, const char *driver_name, FT_Face *aface)
#define ft_isupper(x)
Definition: ftobjs.h:105
GLenum const GLvoid * fontName
unsigned char FT_Byte
Definition: fttypes.h:150
GLenum GLint ref
FT_StreamDesc descriptor
Definition: ftsystem.h:327
FT_Memory memory
Definition: ftobjs.h:860
#define TTAG_LWFN
Definition: tttags.h:72
#define FT_FREE(ptr)
Definition: ftmemory.h:286
GLsizei const GLchar ** path
#define TTAG_POST
Definition: tttags.h:85
GLenum GLsizei len
#define FT_EXPORT_DEF(x)
Definition: ftconfig.h:32
#define FT_FILE
Definition: ftstdlib.h:103
FT_Error error
Definition: cffdrivr.c:411
FT_GetFile_From_Mac_Name(const char *fontName, FSSpec *pathSpec, FT_Long *face_index) FT_DEPRECATED_ATTRIBUTE
GLuint buffer
#define FT_CALLBACK_DEF(x)
Definition: ftconfig.h:323
FT_GetFile_From_Mac_ATS_Name(const char *fontName, FSSpec *pathSpec, FT_Long *face_index) FT_DEPRECATED_ATTRIBUTE
GLintptr offset
#define FALSE
Definition: ftobjs.h:57
#define TTAG_sfnt
Definition: tttags.h:89
typedefFT_BEGIN_HEADER struct FT_MemoryRec_ * FT_Memory
Definition: ftsystem.h:66
local int max
Definition: enough.c:170
short ResourceIndex
Definition: ftmac.c:164
#define TTAG_FOND
Definition: tttags.h:53
#define PATH_MAX
Definition: ftmac.c:92
void * pointer
Definition: ftsystem.h:212
#define PREFER_LWFN
Definition: ftmac.c:171
backing_store_ptr info
Definition: jmemsys.h:181
FT_New_Face_From_FSSpec(FT_Library library, const FSSpec *spec, FT_Long face_index, FT_Face *aface) FT_DEPRECATED_ATTRIBUTE
#define ft_memcmp
Definition: ftstdlib.h:80
#define ft_fclose
Definition: ftstdlib.h:104
GLuint res
FT_Open_Face(FT_Library library, const FT_Open_Args *args, FT_Long face_index, FT_Face *aface)
Definition: ftobjs.c:2005
GLdouble s
FT_New_Face(FT_Library library, const char *filepathname, FT_Long face_index, FT_Face *aface)
Definition: ftobjs.c:1210
#define ft_strncpy
Definition: ftstdlib.h:89
FT_Stream_OpenMemory(FT_Stream stream, const FT_Byte *base, FT_ULong size)
Definition: ftstream.c:35
GLuint GLuint GLsizei count
#define ft_isalnum(x)
Definition: ftobjs.h:109
#define FT_NEW(ptr)
Definition: ftmemory.h:288
#define FT_MEM_COPY(dest, source, count)
Definition: ftmemory.h:203
#define ft_fseek
Definition: ftstdlib.h:107
local int * code
Definition: enough.c:174
#define FT_MEM_SET(dest, byte, count)
Definition: ftmemory.h:201
#define ft_strcpy
Definition: ftstdlib.h:86
#define FT_MEM_MOVE(dest, source, count)
Definition: ftmemory.h:205
#define STREAM_FILE(stream)
Definition: ftsystem.c:242
#define ft_memcpy
Definition: ftstdlib.h:81
GLsizeiptr size
#define ft_strlen
Definition: ftstdlib.h:87
FT_New_Face_From_FOND(FT_Library library, Handle fond, FT_Long face_index, FT_Face *aface) FT_DEPRECATED_ATTRIBUTE
#define SEEK_SET
Definition: zconf.h:249
#define ft_strcmp
Definition: ftstdlib.h:85