T1_Face_Done( T1_Face face ) { FT_Memory memory; T1_Font type1 = &face->type1; if ( face ) { memory = face->root.memory; #ifndef T1_CONFIG_OPTION_NO_MM_SUPPORT /* release multiple masters information */ T1_Done_Blend( face ); face->blend = 0; #endif /* release font info strings */ { PS_FontInfo info = &type1->font_info; FT_FREE( info->version ); FT_FREE( info->notice ); FT_FREE( info->full_name ); FT_FREE( info->family_name ); FT_FREE( info->weight ); } /* release top dictionary */ FT_FREE( type1->charstrings_len ); FT_FREE( type1->charstrings ); FT_FREE( type1->glyph_names ); FT_FREE( type1->subrs ); FT_FREE( type1->subrs_len ); FT_FREE( type1->subrs_block ); FT_FREE( type1->charstrings_block ); FT_FREE( type1->glyph_names_block ); FT_FREE( type1->encoding.char_index ); FT_FREE( type1->encoding.char_name ); FT_FREE( type1->font_name ); #ifndef T1_CONFIG_OPTION_NO_AFM /* release afm data if present */ if ( face->afm_data ) T1_Done_Metrics( memory, (T1_AFM*)face->afm_data ); #endif /* release unicode map, if any */ FT_FREE( face->unicode_map.maps ); face->unicode_map.num_maps = 0; face->root.family_name = 0; face->root.style_name = 0; } }
T1_Face_Done( FT_Face t1face ) /* T1_Face */ { T1_Face face = (T1_Face)t1face; FT_Memory memory; T1_Font type1; if ( !face ) return; memory = face->root.memory; type1 = &face->type1; #ifndef T1_CONFIG_OPTION_NO_MM_SUPPORT /* release multiple masters information */ FT_ASSERT( ( face->len_buildchar == 0 ) == ( face->buildchar == NULL ) ); if ( face->buildchar ) { FT_FREE( face->buildchar ); face->buildchar = NULL; face->len_buildchar = 0; } T1_Done_Blend( face ); face->blend = 0; #endif /* release font info strings */ { PS_FontInfo info = &type1->font_info; FT_FREE( info->version ); FT_FREE( info->notice ); FT_FREE( info->full_name ); FT_FREE( info->family_name ); FT_FREE( info->weight ); } /* release top dictionary */ FT_FREE( type1->charstrings_len ); FT_FREE( type1->charstrings ); FT_FREE( type1->glyph_names ); FT_FREE( type1->subrs ); FT_FREE( type1->subrs_len ); FT_FREE( type1->subrs_block ); FT_FREE( type1->charstrings_block ); FT_FREE( type1->glyph_names_block ); FT_FREE( type1->encoding.char_index ); FT_FREE( type1->encoding.char_name ); FT_FREE( type1->font_name ); #ifndef T1_CONFIG_OPTION_NO_AFM /* release afm data if present */ if ( face->afm_data ) T1_Done_Metrics( memory, (AFM_FontInfo)face->afm_data ); #endif /* release unicode map, if any */ #if 0 FT_FREE( face->unicode_map_rec.maps ); face->unicode_map_rec.num_maps = 0; face->unicode_map = NULL; #endif face->root.family_name = NULL; face->root.style_name = NULL; }
T1_Read_Metrics( FT_Face t1_face, FT_Stream stream ) { PSAux_Service psaux; FT_Memory memory = stream->memory; AFM_ParserRec parser; AFM_FontInfo fi = NULL; FT_Error error = FT_ERR( Unknown_File_Format ); T1_Face face = (T1_Face)t1_face; T1_Font t1_font = &face->type1; if ( face->afm_data ) { FT_TRACE1(( "T1_Read_Metrics:" " Freeing previously attached metrics data.\n" )); T1_Done_Metrics( memory, (AFM_FontInfo)face->afm_data ); face->afm_data = NULL; } if ( FT_NEW( fi ) || FT_FRAME_ENTER( stream->size ) ) goto Exit; fi->FontBBox = t1_font->font_bbox; fi->Ascender = t1_font->font_bbox.yMax; fi->Descender = t1_font->font_bbox.yMin; psaux = (PSAux_Service)face->psaux; if ( psaux->afm_parser_funcs ) { error = psaux->afm_parser_funcs->init( &parser, stream->memory, stream->cursor, stream->limit ); if ( !error ) { parser.FontInfo = fi; parser.get_index = t1_get_index; parser.user_data = t1_font; error = psaux->afm_parser_funcs->parse( &parser ); psaux->afm_parser_funcs->done( &parser ); } } if ( FT_ERR_EQ( error, Unknown_File_Format ) ) { FT_Byte* start = stream->cursor; /* MS Windows allows versions up to 0x3FF without complaining */ if ( stream->size > 6 && start[1] < 4 && FT_PEEK_ULONG_LE( start + 2 ) == stream->size ) error = T1_Read_PFM( t1_face, stream, fi ); } if ( !error ) { t1_font->font_bbox = fi->FontBBox; t1_face->bbox.xMin = fi->FontBBox.xMin >> 16; t1_face->bbox.yMin = fi->FontBBox.yMin >> 16; /* no `U' suffix here to 0xFFFF! */ t1_face->bbox.xMax = ( fi->FontBBox.xMax + 0xFFFF ) >> 16; t1_face->bbox.yMax = ( fi->FontBBox.yMax + 0xFFFF ) >> 16; /* no `U' suffix here to 0x8000! */ t1_face->ascender = (FT_Short)( ( fi->Ascender + 0x8000 ) >> 16 ); t1_face->descender = (FT_Short)( ( fi->Descender + 0x8000 ) >> 16 ); if ( fi->NumKernPair ) { t1_face->face_flags |= FT_FACE_FLAG_KERNING; face->afm_data = fi; fi = NULL; } }