1049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project/***************************************************************************/ 2049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project/* */ 3049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project/* cffparse.c */ 4049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project/* */ 5049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project/* CFF token stream parser (body) */ 6049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project/* */ 7a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang/* Copyright 1996-2004, 2007-2013 by */ 8049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project/* David Turner, Robert Wilhelm, and Werner Lemberg. */ 9049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project/* */ 10049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project/* This file is part of the FreeType project, and may only be used, */ 11049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project/* modified, and distributed under the terms of the FreeType project */ 12049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project/* license, LICENSE.TXT. By continuing to use, modify, or distribute */ 13049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project/* this file you indicate that you have read the license and */ 14049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project/* understand and accept it fully. */ 15049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project/* */ 16049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project/***************************************************************************/ 17049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 18049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 19049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project#include <ft2build.h> 20049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project#include "cffparse.h" 21049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project#include FT_INTERNAL_STREAM_H 22049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project#include FT_INTERNAL_DEBUG_H 23049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 24049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project#include "cfferrs.h" 25295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner#include "cffpic.h" 26049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 27049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 28049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /*************************************************************************/ 29049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* */ 30049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* The macro FT_COMPONENT is used in trace mode. It is an implicit */ 31049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* parameter of the FT_TRACE() and FT_ERROR() macros, used to print/log */ 32049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* messages during execution. */ 33049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* */ 34049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project#undef FT_COMPONENT 35049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project#define FT_COMPONENT trace_cffparse 36049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 37049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 38049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_LOCAL_DEF( void ) 39049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project cff_parser_init( CFF_Parser parser, 40049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_UInt code, 41295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner void* object, 42295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner FT_Library library) 43049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 44049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_MEM_ZERO( parser, sizeof ( *parser ) ); 45049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 46049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project parser->top = parser->stack; 47049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project parser->object_code = code; 48049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project parser->object = object; 49295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner parser->library = library; 50049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 51049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 52049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 53049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* read an integer */ 54049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project static FT_Long 55049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project cff_parse_integer( FT_Byte* start, 56049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Byte* limit ) 57049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 58049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Byte* p = start; 59049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Int v = *p++; 60049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Long val = 0; 61049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 62049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 63049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( v == 28 ) 64049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 65049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( p + 2 > limit ) 66049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project goto Bad; 67049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 68a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang val = (FT_Short)( ( (FT_UShort)p[0] << 8 ) | p[1] ); 69049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project p += 2; 70049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 71049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project else if ( v == 29 ) 72049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 73049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( p + 4 > limit ) 74049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project goto Bad; 75049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 76a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang val = (FT_Long)( ( (FT_ULong)p[0] << 24 ) | 77a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang ( (FT_ULong)p[1] << 16 ) | 78a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang ( (FT_ULong)p[2] << 8 ) | 79a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang (FT_ULong)p[3] ); 80049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project p += 4; 81049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 82049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project else if ( v < 247 ) 83049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 84049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project val = v - 139; 85049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 86049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project else if ( v < 251 ) 87049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 88049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( p + 1 > limit ) 89049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project goto Bad; 90049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 91049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project val = ( v - 247 ) * 256 + p[0] + 108; 92049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project p++; 93049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 94049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project else 95049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 96049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( p + 1 > limit ) 97049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project goto Bad; 98049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 99049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project val = -( v - 251 ) * 256 - p[0] - 108; 100049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project p++; 101049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 102049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 103049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project Exit: 104049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project return val; 105049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 106049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project Bad: 107049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project val = 0; 108a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang FT_TRACE4(( "!!!END OF DATA:!!!" )); 109049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project goto Exit; 110049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 111049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 112049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 113049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project static const FT_Long power_tens[] = 114049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 115049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1L, 116049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 10L, 117049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 100L, 118049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1000L, 119049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 10000L, 120049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 100000L, 121049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1000000L, 122049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 10000000L, 123049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 100000000L, 124049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1000000000L 125049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project }; 126049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 127049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 128049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* read a real */ 129049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project static FT_Fixed 130049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project cff_parse_real( FT_Byte* start, 131049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Byte* limit, 132295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner FT_Long power_ten, 133295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner FT_Long* scaling ) 134049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 135049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Byte* p = start; 136049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_UInt nib; 137049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_UInt phase; 138049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 139aacb8e1368a883fcbc9fe64fd0e460cef9c9b20cNick Kralevich FT_Long result, number, exponent; 140a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang FT_Int sign = 0, exponent_sign = 0, have_overflow = 0; 141295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner FT_Long exponent_add, integer_length, fraction_length; 142049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 143049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 144049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( scaling ) 145aacb8e1368a883fcbc9fe64fd0e460cef9c9b20cNick Kralevich *scaling = 0; 146049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 147049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project result = 0; 148049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 149049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project number = 0; 150049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project exponent = 0; 151049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 152049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project exponent_add = 0; 153049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project integer_length = 0; 154049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project fraction_length = 0; 155049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 156049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* First of all, read the integer part. */ 157049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project phase = 4; 158049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 159049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project for (;;) 160049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 161049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* If we entered this iteration with phase == 4, we need to */ 162049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* read a new byte. This also skips past the initial 0x1E. */ 163049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( phase ) 164049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 165049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project p++; 166049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 167049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* Make sure we don't read past the end. */ 168049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( p >= limit ) 169a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang goto Bad; 170049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 171049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 172049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* Get the nibble. */ 173049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project nib = ( p[0] >> phase ) & 0xF; 174049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project phase = 4 - phase; 175049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 176049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( nib == 0xE ) 177049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project sign = 1; 178049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project else if ( nib > 9 ) 179049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project break; 180049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project else 181049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 182049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* Increase exponent if we can't add the digit. */ 183049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( number >= 0xCCCCCCCL ) 184049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project exponent_add++; 185049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* Skip leading zeros. */ 186049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project else if ( nib || number ) 187049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 188049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project integer_length++; 189049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project number = number * 10 + nib; 190049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 191049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 192049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 193049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 194049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* Read fraction part, if any. */ 195049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( nib == 0xa ) 196049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project for (;;) 197049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 198049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* If we entered this iteration with phase == 4, we need */ 199049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* to read a new byte. */ 200049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( phase ) 201049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 202049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project p++; 203049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 204049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* Make sure we don't read past the end. */ 205049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( p >= limit ) 206a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang goto Bad; 207049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 208049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 209049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* Get the nibble. */ 210049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project nib = ( p[0] >> phase ) & 0xF; 211049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project phase = 4 - phase; 212049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( nib >= 10 ) 213049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project break; 214049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 215049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* Skip leading zeros if possible. */ 216049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( !nib && !number ) 217049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project exponent_add--; 218049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* Only add digit if we don't overflow. */ 21977f63d23f7d380b0ff02c18fd6a154ab9063128aDavid 'Digit' Turner else if ( number < 0xCCCCCCCL && fraction_length < 9 ) 220049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 221049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project fraction_length++; 222049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project number = number * 10 + nib; 223049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 224049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 225049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 226049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* Read exponent, if any. */ 227049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( nib == 12 ) 228049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 229049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project exponent_sign = 1; 230049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project nib = 11; 231049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 232049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 233049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( nib == 11 ) 234049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 235049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project for (;;) 236049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 237049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* If we entered this iteration with phase == 4, */ 238049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* we need to read a new byte. */ 239049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( phase ) 240049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 241049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project p++; 242049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 243049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* Make sure we don't read past the end. */ 244049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( p >= limit ) 245a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang goto Bad; 246049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 247049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 248049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* Get the nibble. */ 249049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project nib = ( p[0] >> phase ) & 0xF; 250049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project phase = 4 - phase; 251049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( nib >= 10 ) 252049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project break; 253049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 254049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* Arbitrarily limit exponent. */ 255049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( exponent > 1000 ) 256a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang have_overflow = 1; 257a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang else 258a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang exponent = exponent * 10 + nib; 259049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 260049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 261049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( exponent_sign ) 262049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project exponent = -exponent; 263049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 264049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 265a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang if ( !number ) 266a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang goto Exit; 267a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang 268a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang if ( have_overflow ) 269a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang { 270a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang if ( exponent_sign ) 271a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang goto Underflow; 272a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang else 273a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang goto Overflow; 274a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang } 275a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang 276049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* We don't check `power_ten' and `exponent_add'. */ 277049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project exponent += power_ten + exponent_add; 278049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 279049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( scaling ) 280049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 281049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* Only use `fraction_length'. */ 282049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project fraction_length += integer_length; 283049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project exponent += integer_length; 284049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 285049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( fraction_length <= 5 ) 286049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 287049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( number > 0x7FFFL ) 288049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 289049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project result = FT_DivFix( number, 10 ); 290049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project *scaling = exponent - fraction_length + 1; 291049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 292049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project else 293049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 294049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( exponent > 0 ) 295049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 296295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner FT_Long new_fraction_length, shift; 297049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 298049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 299049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* Make `scaling' as small as possible. */ 300049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project new_fraction_length = FT_MIN( exponent, 5 ); 301049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project shift = new_fraction_length - fraction_length; 302049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 303a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang if ( shift > 0 ) 304049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 305a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang exponent -= new_fraction_length; 306a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang number *= power_tens[shift]; 307a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang if ( number > 0x7FFFL ) 308a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang { 309a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang number /= 10; 310a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang exponent += 1; 311a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang } 312049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 313a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang else 314a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang exponent -= fraction_length; 315049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 316049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project else 317049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project exponent -= fraction_length; 318049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 319a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang result = (FT_Long)( (FT_ULong)number << 16 ); 320049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project *scaling = exponent; 321049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 322049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 323049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project else 324049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 325049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( ( number / power_tens[fraction_length - 5] ) > 0x7FFFL ) 326049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 327049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project result = FT_DivFix( number, power_tens[fraction_length - 4] ); 328049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project *scaling = exponent - 4; 329049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 330049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project else 331049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 332049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project result = FT_DivFix( number, power_tens[fraction_length - 5] ); 333049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project *scaling = exponent - 5; 334049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 335049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 336049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 337049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project else 338049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 339049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project integer_length += exponent; 340049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project fraction_length -= exponent; 341049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 342a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang if ( integer_length > 5 ) 343a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang goto Overflow; 344a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang if ( integer_length < -5 ) 345a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang goto Underflow; 346049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 34777f63d23f7d380b0ff02c18fd6a154ab9063128aDavid 'Digit' Turner /* Remove non-significant digits. */ 348aacb8e1368a883fcbc9fe64fd0e460cef9c9b20cNick Kralevich if ( integer_length < 0 ) 349aacb8e1368a883fcbc9fe64fd0e460cef9c9b20cNick Kralevich { 35077f63d23f7d380b0ff02c18fd6a154ab9063128aDavid 'Digit' Turner number /= power_tens[-integer_length]; 35177f63d23f7d380b0ff02c18fd6a154ab9063128aDavid 'Digit' Turner fraction_length += integer_length; 35277f63d23f7d380b0ff02c18fd6a154ab9063128aDavid 'Digit' Turner } 35377f63d23f7d380b0ff02c18fd6a154ab9063128aDavid 'Digit' Turner 354aacb8e1368a883fcbc9fe64fd0e460cef9c9b20cNick Kralevich /* this can only happen if exponent was non-zero */ 355aacb8e1368a883fcbc9fe64fd0e460cef9c9b20cNick Kralevich if ( fraction_length == 10 ) 356aacb8e1368a883fcbc9fe64fd0e460cef9c9b20cNick Kralevich { 357aacb8e1368a883fcbc9fe64fd0e460cef9c9b20cNick Kralevich number /= 10; 358aacb8e1368a883fcbc9fe64fd0e460cef9c9b20cNick Kralevich fraction_length -= 1; 359aacb8e1368a883fcbc9fe64fd0e460cef9c9b20cNick Kralevich } 360aacb8e1368a883fcbc9fe64fd0e460cef9c9b20cNick Kralevich 361049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* Convert into 16.16 format. */ 362049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( fraction_length > 0 ) 363049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 364049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( ( number / power_tens[fraction_length] ) > 0x7FFFL ) 365049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project goto Exit; 366049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 367049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project result = FT_DivFix( number, power_tens[fraction_length] ); 368049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 369049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project else 370049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 371049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project number *= power_tens[-fraction_length]; 372049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 373049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( number > 0x7FFFL ) 374a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang goto Overflow; 375049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 376a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang result = (FT_Long)( (FT_ULong)number << 16 ); 377049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 378049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 379049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 380a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang Exit: 381049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( sign ) 382049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project result = -result; 383049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 384049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project return result; 385a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang 386a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang Overflow: 387a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang result = 0x7FFFFFFFL; 388a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang FT_TRACE4(( "!!!OVERFLOW:!!!" )); 389a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang goto Exit; 390a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang 391a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang Underflow: 392a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang result = 0; 393a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang FT_TRACE4(( "!!!UNDERFLOW:!!!" )); 394a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang goto Exit; 395a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang 396a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang Bad: 397a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang result = 0; 398a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang FT_TRACE4(( "!!!END OF DATA:!!!" )); 399a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang goto Exit; 400049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 401049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 402049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 403049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* read a number, either integer or real */ 404049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project static FT_Long 405049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project cff_parse_num( FT_Byte** d ) 406049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 407049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project return **d == 30 ? ( cff_parse_real( d[0], d[1], 0, NULL ) >> 16 ) 408049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project : cff_parse_integer( d[0], d[1] ); 409049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 410049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 411049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 412049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* read a floating point number, either integer or real */ 413049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project static FT_Fixed 414a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang do_fixed( FT_Byte** d, 415a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang FT_Long scaling ) 416a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang { 417a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang if ( **d == 30 ) 418a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang return cff_parse_real( d[0], d[1], scaling, NULL ); 419a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang else 420a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang { 421a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang FT_Long val = cff_parse_integer( d[0], d[1] ); 422a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang 423a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang 424a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang if ( scaling ) 425a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang val *= power_tens[scaling]; 426a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang 427a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang if ( val > 0x7FFF ) 428a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang { 429a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang val = 0x7FFFFFFFL; 430a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang goto Overflow; 431a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang } 432a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang else if ( val < -0x7FFF ) 433a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang { 434a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang val = -0x7FFFFFFFL; 435a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang goto Overflow; 436a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang } 437a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang 438a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang return (FT_Long)( (FT_ULong)val << 16 ); 439a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang 440a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang Overflow: 441a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang FT_TRACE4(( "!!!OVERFLOW:!!!" )); 442a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang return val; 443a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang } 444a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang } 445a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang 446a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang 447a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang /* read a floating point number, either integer or real */ 448a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang static FT_Fixed 449049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project cff_parse_fixed( FT_Byte** d ) 450049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 451a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang return do_fixed( d, 0 ); 452049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 453049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 454049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 455049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* read a floating point number, either integer or real, */ 456049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* but return `10^scaling' times the number read in */ 457049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project static FT_Fixed 458049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project cff_parse_fixed_scaled( FT_Byte** d, 459295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner FT_Long scaling ) 460049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 461a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang return do_fixed( d, scaling ); 462049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 463049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 464049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 465049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* read a floating point number, either integer or real, */ 466049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* and return it as precise as possible -- `scaling' returns */ 467049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* the scaling factor (as a power of 10) */ 468049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project static FT_Fixed 469049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project cff_parse_fixed_dynamic( FT_Byte** d, 470295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner FT_Long* scaling ) 471049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 472049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_ASSERT( scaling ); 473049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 474049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( **d == 30 ) 475049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project return cff_parse_real( d[0], d[1], 0, scaling ); 476049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project else 477049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 478049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Long number; 479049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Int integer_length; 480049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 481049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 482049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project number = cff_parse_integer( d[0], d[1] ); 483049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 484049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( number > 0x7FFFL ) 485049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 486049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project for ( integer_length = 5; integer_length < 10; integer_length++ ) 487049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( number < power_tens[integer_length] ) 488049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project break; 489049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 490049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( ( number / power_tens[integer_length - 5] ) > 0x7FFFL ) 491049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 492049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project *scaling = integer_length - 4; 493049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project return FT_DivFix( number, power_tens[integer_length - 4] ); 494049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 495049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project else 496049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 497049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project *scaling = integer_length - 5; 498049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project return FT_DivFix( number, power_tens[integer_length - 5] ); 499049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 500049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 501049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project else 502049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 503049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project *scaling = 0; 504a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang return (FT_Long)( (FT_ULong)number << 16 ); 505049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 506049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 507049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 508049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 509049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 510049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project static FT_Error 511049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project cff_parse_font_matrix( CFF_Parser parser ) 512049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 513049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project CFF_FontRecDict dict = (CFF_FontRecDict)parser->object; 514049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Matrix* matrix = &dict->font_matrix; 515049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Vector* offset = &dict->font_offset; 516049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_ULong* upm = &dict->units_per_em; 517049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Byte** data = parser->stack; 518a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang FT_Error error = FT_ERR( Stack_Underflow ); 519049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 520049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 521049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( parser->top >= parser->stack + 6 ) 522049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 523295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner FT_Long scaling; 524049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 525049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 526a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang error = FT_Err_Ok; 527049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 528e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang dict->has_font_matrix = TRUE; 529e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 530049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* We expect a well-formed font matrix, this is, the matrix elements */ 531049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* `xx' and `yy' are of approximately the same magnitude. To avoid */ 532049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* loss of precision, we use the magnitude of element `xx' to scale */ 533049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* all other elements. The scaling factor is then contained in the */ 534049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* `units_per_em' value. */ 535049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 536049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project matrix->xx = cff_parse_fixed_dynamic( data++, &scaling ); 537049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 538049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project scaling = -scaling; 539049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 540049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( scaling < 0 || scaling > 9 ) 541049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 542049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* Return default matrix in case of unlikely values. */ 543c3ee10bfa1f76a18500b487de9c85757375b48f3David 'Digit' Turner 544c3ee10bfa1f76a18500b487de9c85757375b48f3David 'Digit' Turner FT_TRACE1(( "cff_parse_font_matrix:" 545c3ee10bfa1f76a18500b487de9c85757375b48f3David 'Digit' Turner " strange scaling value for xx element (%d),\n" 546c3ee10bfa1f76a18500b487de9c85757375b48f3David 'Digit' Turner " " 547c3ee10bfa1f76a18500b487de9c85757375b48f3David 'Digit' Turner " using default matrix\n", scaling )); 548c3ee10bfa1f76a18500b487de9c85757375b48f3David 'Digit' Turner 549049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project matrix->xx = 0x10000L; 550049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project matrix->yx = 0; 551c3ee10bfa1f76a18500b487de9c85757375b48f3David 'Digit' Turner matrix->xy = 0; 552049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project matrix->yy = 0x10000L; 553049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project offset->x = 0; 554049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project offset->y = 0; 555049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project *upm = 1; 556049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 557049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project goto Exit; 558049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 559049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 560049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project matrix->yx = cff_parse_fixed_scaled( data++, scaling ); 561049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project matrix->xy = cff_parse_fixed_scaled( data++, scaling ); 562049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project matrix->yy = cff_parse_fixed_scaled( data++, scaling ); 563049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project offset->x = cff_parse_fixed_scaled( data++, scaling ); 564049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project offset->y = cff_parse_fixed_scaled( data, scaling ); 565049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 566049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project *upm = power_tens[scaling]; 567c3ee10bfa1f76a18500b487de9c85757375b48f3David 'Digit' Turner 568e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_TRACE4(( " [%f %f %f %f %f %f]\n", 569c3ee10bfa1f76a18500b487de9c85757375b48f3David 'Digit' Turner (double)matrix->xx / *upm / 65536, 570c3ee10bfa1f76a18500b487de9c85757375b48f3David 'Digit' Turner (double)matrix->xy / *upm / 65536, 571c3ee10bfa1f76a18500b487de9c85757375b48f3David 'Digit' Turner (double)matrix->yx / *upm / 65536, 572e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang (double)matrix->yy / *upm / 65536, 573e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang (double)offset->x / *upm / 65536, 574e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang (double)offset->y / *upm / 65536 )); 575049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 576049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 577049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project Exit: 578049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project return error; 579049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 580049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 581049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 582049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project static FT_Error 583049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project cff_parse_font_bbox( CFF_Parser parser ) 584049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 585049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project CFF_FontRecDict dict = (CFF_FontRecDict)parser->object; 586049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_BBox* bbox = &dict->font_bbox; 587049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Byte** data = parser->stack; 588049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Error error; 589049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 590049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 591a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang error = FT_ERR( Stack_Underflow ); 592049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 593049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( parser->top >= parser->stack + 4 ) 594049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 595049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project bbox->xMin = FT_RoundFix( cff_parse_fixed( data++ ) ); 596049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project bbox->yMin = FT_RoundFix( cff_parse_fixed( data++ ) ); 597049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project bbox->xMax = FT_RoundFix( cff_parse_fixed( data++ ) ); 598049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project bbox->yMax = FT_RoundFix( cff_parse_fixed( data ) ); 599a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang error = FT_Err_Ok; 600c3ee10bfa1f76a18500b487de9c85757375b48f3David 'Digit' Turner 601e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_TRACE4(( " [%d %d %d %d]\n", 602c3ee10bfa1f76a18500b487de9c85757375b48f3David 'Digit' Turner bbox->xMin / 65536, 603c3ee10bfa1f76a18500b487de9c85757375b48f3David 'Digit' Turner bbox->yMin / 65536, 604c3ee10bfa1f76a18500b487de9c85757375b48f3David 'Digit' Turner bbox->xMax / 65536, 605c3ee10bfa1f76a18500b487de9c85757375b48f3David 'Digit' Turner bbox->yMax / 65536 )); 606049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 607049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 608049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project return error; 609049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 610049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 611049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 612049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project static FT_Error 613049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project cff_parse_private_dict( CFF_Parser parser ) 614049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 615049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project CFF_FontRecDict dict = (CFF_FontRecDict)parser->object; 616049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Byte** data = parser->stack; 617049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Error error; 618049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 619049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 620a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang error = FT_ERR( Stack_Underflow ); 621049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 622049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( parser->top >= parser->stack + 2 ) 623049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 624049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project dict->private_size = cff_parse_num( data++ ); 625049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project dict->private_offset = cff_parse_num( data ); 626e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_TRACE4(( " %lu %lu\n", 627e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang dict->private_size, dict->private_offset )); 628e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 629a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang error = FT_Err_Ok; 630049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 631049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 632049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project return error; 633049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 634049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 635049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 636049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project static FT_Error 637049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project cff_parse_cid_ros( CFF_Parser parser ) 638049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 639049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project CFF_FontRecDict dict = (CFF_FontRecDict)parser->object; 640049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Byte** data = parser->stack; 641049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Error error; 642049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 643049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 644a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang error = FT_ERR( Stack_Underflow ); 645049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 646049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( parser->top >= parser->stack + 3 ) 647049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 648e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang dict->cid_registry = (FT_UInt)cff_parse_num( data++ ); 649e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang dict->cid_ordering = (FT_UInt)cff_parse_num( data++ ); 650295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner if ( **data == 30 ) 651295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner FT_TRACE1(( "cff_parse_cid_ros: real supplement is rounded\n" )); 652295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner dict->cid_supplement = cff_parse_num( data ); 653295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner if ( dict->cid_supplement < 0 ) 654295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner FT_TRACE1(( "cff_parse_cid_ros: negative supplement %d is found\n", 655295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner dict->cid_supplement )); 656a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang error = FT_Err_Ok; 657c3ee10bfa1f76a18500b487de9c85757375b48f3David 'Digit' Turner 658e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_TRACE4(( " %d %d %d\n", 659c3ee10bfa1f76a18500b487de9c85757375b48f3David 'Digit' Turner dict->cid_registry, 660c3ee10bfa1f76a18500b487de9c85757375b48f3David 'Digit' Turner dict->cid_ordering, 661c3ee10bfa1f76a18500b487de9c85757375b48f3David 'Digit' Turner dict->cid_supplement )); 662049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 663049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 664049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project return error; 665049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 666049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 667049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 668e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#define CFF_FIELD_NUM( code, name, id ) \ 669e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang CFF_FIELD( code, name, id, cff_kind_num ) 670e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#define CFF_FIELD_FIXED( code, name, id ) \ 671e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang CFF_FIELD( code, name, id, cff_kind_fixed ) 672e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#define CFF_FIELD_FIXED_1000( code, name, id ) \ 673e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang CFF_FIELD( code, name, id, cff_kind_fixed_thousand ) 674e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#define CFF_FIELD_STRING( code, name, id ) \ 675e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang CFF_FIELD( code, name, id, cff_kind_string ) 676e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#define CFF_FIELD_BOOL( code, name, id ) \ 677e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang CFF_FIELD( code, name, id, cff_kind_bool ) 678049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 679295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner#define CFFCODE_TOPDICT 0x1000 680295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner#define CFFCODE_PRIVATE 0x2000 681295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner 682e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 683295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner#ifndef FT_CONFIG_OPTION_PIC 684295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner 685049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 686049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project#undef CFF_FIELD 687e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#undef CFF_FIELD_DELTA 688e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 689e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 690e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#ifndef FT_DEBUG_LEVEL_TRACE 691e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 692e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 693e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#define CFF_FIELD_CALLBACK( code, name, id ) \ 694e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang { \ 695e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang cff_kind_callback, \ 696e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang code | CFFCODE, \ 697e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 0, 0, \ 698e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang cff_parse_ ## name, \ 699e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 0, 0 \ 700049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project }, 701049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 702e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#define CFF_FIELD( code, name, id, kind ) \ 703e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang { \ 704e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang kind, \ 705e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang code | CFFCODE, \ 706e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_FIELD_OFFSET( name ), \ 707e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_FIELD_SIZE( name ), \ 708e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 0, 0, 0 \ 709e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang }, 710e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 711e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#define CFF_FIELD_DELTA( code, name, max, id ) \ 712e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang { \ 713e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang cff_kind_delta, \ 714e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang code | CFFCODE, \ 715e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_FIELD_OFFSET( name ), \ 716e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_FIELD_SIZE_DELTA( name ), \ 717e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 0, \ 718e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang max, \ 719e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_FIELD_OFFSET( num_ ## name ) \ 720e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang }, 721049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 722049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project static const CFF_Field_Handler cff_field_handlers[] = 723049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 724049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 725049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project#include "cfftoken.h" 726049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 727049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 0, 0, 0, 0, 0, 0, 0 } 728049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project }; 729049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 730049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 731e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#else /* FT_DEBUG_LEVEL_TRACE */ 732e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 733e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 734e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 735e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#define CFF_FIELD_CALLBACK( code, name, id ) \ 736e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang { \ 737e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang cff_kind_callback, \ 738e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang code | CFFCODE, \ 739e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 0, 0, \ 740e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang cff_parse_ ## name, \ 741e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 0, 0, \ 742e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang id \ 743e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang }, 744e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 745e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#define CFF_FIELD( code, name, id, kind ) \ 746e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang { \ 747e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang kind, \ 748e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang code | CFFCODE, \ 749e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_FIELD_OFFSET( name ), \ 750e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_FIELD_SIZE( name ), \ 751e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 0, 0, 0, \ 752e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang id \ 753e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang }, 754e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 755e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#define CFF_FIELD_DELTA( code, name, max, id ) \ 756e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang { \ 757e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang cff_kind_delta, \ 758e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang code | CFFCODE, \ 759e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_FIELD_OFFSET( name ), \ 760e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_FIELD_SIZE_DELTA( name ), \ 761e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 0, \ 762e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang max, \ 763e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_FIELD_OFFSET( num_ ## name ), \ 764e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang id \ 765e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang }, 766e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 767e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang static const CFF_Field_Handler cff_field_handlers[] = 768e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang { 769e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 770e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#include "cfftoken.h" 771e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 772e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang { 0, 0, 0, 0, 0, 0, 0, 0 } 773e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang }; 774e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 775e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 776e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#endif /* FT_DEBUG_LEVEL_TRACE */ 777e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 778e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 779295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner#else /* FT_CONFIG_OPTION_PIC */ 780295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner 781e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 782e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang void 783e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_Destroy_Class_cff_field_handlers( FT_Library library, 784e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang CFF_Field_Handler* clazz ) 785295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner { 786e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_Memory memory = library->memory; 787e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 788e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 789295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner if ( clazz ) 790295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner FT_FREE( clazz ); 791295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner } 792295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner 793e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 794e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_Error 795e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_Create_Class_cff_field_handlers( FT_Library library, 796e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang CFF_Field_Handler** output_class ) 797295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner { 798a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang CFF_Field_Handler* clazz = NULL; 799e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_Error error; 800e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_Memory memory = library->memory; 801e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 802e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang int i = 0; 803e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 804295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner 805295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner#undef CFF_FIELD 806e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#define CFF_FIELD( code, name, id, kind ) i++; 807295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner#undef CFF_FIELD_DELTA 808e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#define CFF_FIELD_DELTA( code, name, max, id ) i++; 809295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner#undef CFF_FIELD_CALLBACK 810e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#define CFF_FIELD_CALLBACK( code, name, id ) i++; 811295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner 812295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner#include "cfftoken.h" 813295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner 814e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang i++; /* { 0, 0, 0, 0, 0, 0, 0 } */ 815e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 816e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang if ( FT_ALLOC( clazz, sizeof ( CFF_Field_Handler ) * i ) ) 817295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner return error; 818295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner 819e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang i = 0; 820e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 821e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 822e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#ifndef FT_DEBUG_LEVEL_TRACE 823e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 824e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 825295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner#undef CFF_FIELD_CALLBACK 826e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#define CFF_FIELD_CALLBACK( code_, name_, id_ ) \ 827e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].kind = cff_kind_callback; \ 828e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].code = code_ | CFFCODE; \ 829e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].offset = 0; \ 830e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].size = 0; \ 831e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].reader = cff_parse_ ## name_; \ 832e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].array_max = 0; \ 833e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].count_offset = 0; \ 834e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang i++; 835e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 836e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#undef CFF_FIELD 837e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#define CFF_FIELD( code_, name_, id_, kind_ ) \ 838e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].kind = kind_; \ 839e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].code = code_ | CFFCODE; \ 840e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].offset = FT_FIELD_OFFSET( name_ ); \ 841e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].size = FT_FIELD_SIZE( name_ ); \ 842e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].reader = 0; \ 843e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].array_max = 0; \ 844e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].count_offset = 0; \ 845e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang i++; \ 846e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 847e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#undef CFF_FIELD_DELTA 848e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#define CFF_FIELD_DELTA( code_, name_, max_, id_ ) \ 849e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].kind = cff_kind_delta; \ 850e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].code = code_ | CFFCODE; \ 851e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].offset = FT_FIELD_OFFSET( name_ ); \ 852e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].size = FT_FIELD_SIZE_DELTA( name_ ); \ 853e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].reader = 0; \ 854e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].array_max = max_; \ 855e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].count_offset = FT_FIELD_OFFSET( num_ ## name_ ); \ 856e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang i++; 857295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner 858e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#include "cfftoken.h" 859e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 860e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].kind = 0; 861e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].code = 0; 862e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].offset = 0; 863e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].size = 0; 864e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].reader = 0; 865e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].array_max = 0; 866e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].count_offset = 0; 867e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 868e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 869e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#else /* FT_DEBUG_LEVEL_TRACE */ 870e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 871e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 872e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#undef CFF_FIELD_CALLBACK 873e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#define CFF_FIELD_CALLBACK( code_, name_, id_ ) \ 874e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].kind = cff_kind_callback; \ 875e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].code = code_ | CFFCODE; \ 876e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].offset = 0; \ 877e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].size = 0; \ 878e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].reader = cff_parse_ ## name_; \ 879e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].array_max = 0; \ 880e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].count_offset = 0; \ 881e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].id = id_; \ 882e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang i++; 883295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner 884295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner#undef CFF_FIELD 885e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#define CFF_FIELD( code_, name_, id_, kind_ ) \ 886e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].kind = kind_; \ 887e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].code = code_ | CFFCODE; \ 888e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].offset = FT_FIELD_OFFSET( name_ ); \ 889e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].size = FT_FIELD_SIZE( name_ ); \ 890e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].reader = 0; \ 891e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].array_max = 0; \ 892e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].count_offset = 0; \ 893e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].id = id_; \ 894e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang i++; \ 895295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner 896295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner#undef CFF_FIELD_DELTA 897e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#define CFF_FIELD_DELTA( code_, name_, max_, id_ ) \ 898e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].kind = cff_kind_delta; \ 899e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].code = code_ | CFFCODE; \ 900e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].offset = FT_FIELD_OFFSET( name_ ); \ 901e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].size = FT_FIELD_SIZE_DELTA( name_ ); \ 902e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].reader = 0; \ 903e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].array_max = max_; \ 904e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].count_offset = FT_FIELD_OFFSET( num_ ## name_ ); \ 905e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].id = id_; \ 906e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang i++; 907295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner 908295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner#include "cfftoken.h" 909295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner 910e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].kind = 0; 911e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].code = 0; 912e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].offset = 0; 913e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].size = 0; 914e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].reader = 0; 915e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].array_max = 0; 916295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner clazz[i].count_offset = 0; 917e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang clazz[i].id = 0; 918e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 919e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 920e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#endif /* FT_DEBUG_LEVEL_TRACE */ 921e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 922295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner 923295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner *output_class = clazz; 924e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 925a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang return FT_Err_Ok; 926295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner } 927295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner 928295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner 929295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner#endif /* FT_CONFIG_OPTION_PIC */ 930295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner 931295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner 932049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_LOCAL_DEF( FT_Error ) 933049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project cff_parser_run( CFF_Parser parser, 934049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Byte* start, 935049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Byte* limit ) 936049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 937295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner FT_Byte* p = start; 938a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang FT_Error error = FT_Err_Ok; 939295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner FT_Library library = parser->library; 940e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_UNUSED( library ); 941049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 942049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 943049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project parser->top = parser->stack; 944049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project parser->start = start; 945049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project parser->limit = limit; 946049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project parser->cursor = start; 947049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 948049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project while ( p < limit ) 949049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 950049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_UInt v = *p; 951049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 952049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 953049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( v >= 27 && v != 31 ) 954049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 955049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* it's a number; we will push its position on the stack */ 956049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( parser->top - parser->stack >= CFF_MAX_STACK_DEPTH ) 957049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project goto Stack_Overflow; 958049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 959049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project *parser->top ++ = p; 960049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 961049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* now, skip it */ 962049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( v == 30 ) 963049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 964049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* skip real number */ 965049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project p++; 966049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project for (;;) 967049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 968295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner /* An unterminated floating point number at the */ 969295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner /* end of a dictionary is invalid but harmless. */ 970049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( p >= limit ) 971295ffce55e0198e7a9f7d46b33f5c2b4147bf821David 'Digit' Turner goto Exit; 972049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project v = p[0] >> 4; 973049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( v == 15 ) 974049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project break; 975049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project v = p[0] & 0xF; 976049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( v == 15 ) 977049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project break; 978049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project p++; 979049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 980049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 981049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project else if ( v == 28 ) 982049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project p += 2; 983049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project else if ( v == 29 ) 984049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project p += 4; 985049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project else if ( v > 246 ) 986049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project p += 1; 987049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 988049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project else 989049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 990049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* This is not a number, hence it's an operator. Compute its code */ 991049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* and look for it in our current list. */ 992049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 993049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_UInt code; 994049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_UInt num_args = (FT_UInt) 995049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project ( parser->top - parser->stack ); 996049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project const CFF_Field_Handler* field; 997049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 998049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 999049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project *parser->top = p; 1000049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project code = v; 1001049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( v == 12 ) 1002049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 1003049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* two byte operator */ 1004049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project p++; 1005049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( p >= limit ) 1006049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project goto Syntax_Error; 1007049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1008049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project code = 0x100 | p[0]; 1009049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 1010049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project code = code | parser->object_code; 1011049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1012a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang for ( field = CFF_FIELD_HANDLERS_GET; field->kind; field++ ) 1013049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 1014049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( field->code == (FT_Int)code ) 1015049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 1016049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* we found our field's handler; read it */ 1017049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Long val; 1018049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Byte* q = (FT_Byte*)parser->object + field->offset; 1019049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1020049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1021e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#ifdef FT_DEBUG_LEVEL_TRACE 1022e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_TRACE4(( " %s", field->id )); 1023e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#endif 1024e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 1025049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* check that we have enough arguments -- except for */ 1026049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* delta encoded arrays, which can be empty */ 1027049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( field->kind != cff_kind_delta && num_args < 1 ) 1028049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project goto Stack_Underflow; 1029049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1030049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project switch ( field->kind ) 1031049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 1032049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project case cff_kind_bool: 1033049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project case cff_kind_string: 1034049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project case cff_kind_num: 1035049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project val = cff_parse_num( parser->stack ); 1036049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project goto Store_Number; 1037049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1038049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project case cff_kind_fixed: 1039049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project val = cff_parse_fixed( parser->stack ); 1040049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project goto Store_Number; 1041049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1042049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project case cff_kind_fixed_thousand: 1043049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project val = cff_parse_fixed_scaled( parser->stack, 3 ); 1044049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1045049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project Store_Number: 1046049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project switch ( field->size ) 1047049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 1048049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project case (8 / FT_CHAR_BIT): 1049049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project *(FT_Byte*)q = (FT_Byte)val; 1050049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project break; 1051049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1052049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project case (16 / FT_CHAR_BIT): 1053049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project *(FT_Short*)q = (FT_Short)val; 1054049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project break; 1055049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1056049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project case (32 / FT_CHAR_BIT): 1057049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project *(FT_Int32*)q = (FT_Int)val; 1058049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project break; 1059049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1060049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project default: /* for 64-bit systems */ 1061049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project *(FT_Long*)q = val; 1062049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 1063e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 1064e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#ifdef FT_DEBUG_LEVEL_TRACE 1065e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang switch ( field->kind ) 1066e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang { 1067e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang case cff_kind_bool: 1068e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_TRACE4(( " %s\n", val ? "true" : "false" )); 1069e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang break; 1070e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 1071e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang case cff_kind_string: 1072e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_TRACE4(( " %ld (SID)\n", val )); 1073e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang break; 1074e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 1075e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang case cff_kind_num: 1076e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_TRACE4(( " %ld\n", val )); 1077e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang break; 1078e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 1079e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang case cff_kind_fixed: 1080e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_TRACE4(( " %f\n", (double)val / 65536 )); 1081e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang break; 1082e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 1083e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang case cff_kind_fixed_thousand: 1084e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_TRACE4(( " %f\n", (double)val / 65536 / 1000 )); 1085e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 1086e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang default: 1087e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang ; /* never reached */ 1088e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang } 1089e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang#endif 1090e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 1091049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project break; 1092049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1093049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project case cff_kind_delta: 1094049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 1095049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Byte* qcount = (FT_Byte*)parser->object + 1096049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project field->count_offset; 1097049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1098049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project FT_Byte** data = parser->stack; 1099049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1100049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1101049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( num_args > field->array_max ) 1102049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project num_args = field->array_max; 1103049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1104e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_TRACE4(( " [" )); 1105e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 1106049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* store count */ 1107049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project *qcount = (FT_Byte)num_args; 1108049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1109049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project val = 0; 1110049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project while ( num_args > 0 ) 1111049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 1112049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project val += cff_parse_num( data++ ); 1113049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project switch ( field->size ) 1114049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project { 1115049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project case (8 / FT_CHAR_BIT): 1116049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project *(FT_Byte*)q = (FT_Byte)val; 1117049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project break; 1118049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1119049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project case (16 / FT_CHAR_BIT): 1120049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project *(FT_Short*)q = (FT_Short)val; 1121049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project break; 1122049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1123049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project case (32 / FT_CHAR_BIT): 1124049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project *(FT_Int32*)q = (FT_Int)val; 1125049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project break; 1126049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1127049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project default: /* for 64-bit systems */ 1128049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project *(FT_Long*)q = val; 1129049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 1130049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1131e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_TRACE4(( " %ld", val )); 1132e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 1133049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project q += field->size; 1134049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project num_args--; 1135049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 1136e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang 1137e3b631da8034f7c6ecc6d809cd9e46d306215c32Xianzhu Wang FT_TRACE4(( "]\n" )); 1138049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 1139049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project break; 1140049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1141049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project default: /* callback */ 1142049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project error = field->reader( parser ); 1143049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project if ( error ) 1144049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project goto Exit; 1145049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 1146049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project goto Found; 1147049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 1148049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 1149049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1150049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* this is an unknown operator, or it is unsupported; */ 1151049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* we will ignore it for now. */ 1152049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1153049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project Found: 1154049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project /* clear stack */ 1155049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project parser->top = parser->stack; 1156049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 1157049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project p++; 1158049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 1159049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1160049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project Exit: 1161049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project return error; 1162049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1163049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project Stack_Overflow: 1164a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang error = FT_THROW( Invalid_Argument ); 1165049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project goto Exit; 1166049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1167049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project Stack_Underflow: 1168a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang error = FT_THROW( Invalid_Argument ); 1169049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project goto Exit; 1170049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1171049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project Syntax_Error: 1172a2b9955b49034a51dfbc8bf9f4e9d312149cecacXianzhu Wang error = FT_THROW( Invalid_Argument ); 1173049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project goto Exit; 1174049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project } 1175049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1176049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project 1177049d6fea481044fcc000e7782e5bc7046fc70844The Android Open Source Project/* END */ 1178