1 /***************************************************************************/ 2 /* */ 3 /* cidparse.c */ 4 /* */ 5 /* CID-keyed Type1 parser (body). */ 6 /* */ 7 /* Copyright 1996-2001, 2002 by */ 8 /* David Turner, Robert Wilhelm, and Werner Lemberg. */ 9 /* */ 10 /* This file is part of the FreeType project, and may only be used, */ 11 /* modified, and distributed under the terms of the FreeType project */ 12 /* license, LICENSE.TXT. By continuing to use, modify, or distribute */ 13 /* this file you indicate that you have read the license and */ 14 /* understand and accept it fully. */ 15 /* */ 16 /***************************************************************************/ 17 18 19 #include <ft2build.h> 20 #include FT_INTERNAL_DEBUG_H 21 #include FT_INTERNAL_CALC_H 22 #include FT_INTERNAL_OBJECTS_H 23 #include FT_INTERNAL_STREAM_H 24 25 #include "cidparse.h" 26 27 #include "ciderrs.h" 28 29 30 /*************************************************************************/ 31 /* */ 32 /* The macro FT_COMPONENT is used in trace mode. It is an implicit */ 33 /* parameter of the FT_TRACE() and FT_ERROR() macros, used to print/log */ 34 /* messages during execution. */ 35 /* */ 36 #undef FT_COMPONENT 37 #define FT_COMPONENT trace_cidparse 38 39 40 /*************************************************************************/ 41 /*************************************************************************/ 42 /*************************************************************************/ 43 /***** *****/ 44 /***** INPUT STREAM PARSER *****/ 45 /***** *****/ 46 /*************************************************************************/ 47 /*************************************************************************/ 48 /*************************************************************************/ 49 50 51 FT_LOCAL_DEF( FT_Error ) 52 cid_parser_new( CID_Parser* parser, 53 FT_Stream stream, 54 FT_Memory memory, 55 PSAux_Service psaux ) 56 { 57 FT_Error error; 58 FT_ULong base_offset, offset, ps_len; 59 FT_Byte buffer[256 + 10]; 60 FT_Int buff_len; 61 62 63 FT_MEM_ZERO( parser, sizeof ( *parser ) ); 64 psaux->ps_parser_funcs->init( &parser->root, 0, 0, memory ); 65 66 parser->stream = stream; 67 68 base_offset = FT_STREAM_POS(); 69 70 /* first of all, check the font format in the header */ 71 if ( FT_FRAME_ENTER( 31 ) ) 72 goto Exit; 73 74 if ( ft_strncmp( (char *)stream->cursor, 75 "%!PS-Adobe-3.0 Resource-CIDFont", 31 ) ) 76 { 77 FT_TRACE2(( "[not a valid CID-keyed font]\n" )); 78 error = CID_Err_Unknown_File_Format; 79 } 80 81 FT_FRAME_EXIT(); 82 if ( error ) 83 goto Exit; 84 85 /* now, read the rest of the file, until we find a `StartData' */ 86 buff_len = 256; 87 for (;;) 88 { 89 FT_Byte *p, *limit = buffer + 256; 90 FT_ULong top_position; 91 92 93 /* fill input buffer */ 94 buff_len -= 256; 95 if ( buff_len > 0 ) 96 FT_MEM_MOVE( buffer, limit, buff_len ); 97 98 p = buffer + buff_len; 99 100 if ( FT_STREAM_READ( p, 256 + 10 - buff_len ) ) 101 goto Exit; 102 103 top_position = FT_STREAM_POS() - buff_len; 104 buff_len = 256 + 10; 105 106 /* look for `StartData' */ 107 for ( p = buffer; p < limit; p++ ) 108 { 109 if ( p[0] == 'S' && ft_strncmp( (char*)p, "StartData", 9 ) == 0 ) 110 { 111 /* save offset of binary data after `StartData' */ 112 offset = (FT_ULong)( top_position - ( limit - p ) + 10 ); 113 goto Found; 114 } 115 } 116 } 117 118 Found: 119 /* we have found the start of the binary data. We will now */ 120 /* rewind and extract the frame of corresponding to the Postscript */ 121 /* section */ 122 123 ps_len = offset - base_offset; 124 if ( FT_STREAM_SEEK( base_offset ) || 125 FT_FRAME_EXTRACT( ps_len, parser->postscript ) ) 126 goto Exit; 127 128 parser->data_offset = offset; 129 parser->postscript_len = ps_len; 130 parser->root.base = parser->postscript; 131 parser->root.cursor = parser->postscript; 132 parser->root.limit = parser->root.cursor + ps_len; 133 parser->num_dict = -1; 134 135 Exit: 136 return error; 137 } 138 139 140 FT_LOCAL_DEF( void ) 141 cid_parser_done( CID_Parser* parser ) 142 { 143 /* always free the private dictionary */ 144 if ( parser->postscript ) 145 { 146 FT_Stream stream = parser->stream; 147 148 149 FT_FRAME_RELEASE( parser->postscript ); 150 } 151 parser->root.funcs.done( &parser->root ); 152 } 153 154 155 /* END */ 156