⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ttcmap.c

📁 奇趣公司比较新的qt/emd版本
💻 C
📖 第 1 页 / 共 5 页
字号:
/***************************************************************************//*                                                                         *//*  ttcmap.c                                                               *//*                                                                         *//*    TrueType character mapping table (cmap) support (body).              *//*                                                                         *//*  Copyright 2002, 2003, 2004, 2005, 2006, 2007 by                        *//*  David Turner, Robert Wilhelm, and Werner Lemberg.                      *//*                                                                         *//*  This file is part of the FreeType project, and may only be used,       *//*  modified, and distributed under the terms of the FreeType project      *//*  license, LICENSE.TXT.  By continuing to use, modify, or distribute     *//*  this file you indicate that you have read the license and              *//*  understand and accept it fully.                                        *//*                                                                         *//***************************************************************************/#include <ft2build.h>#include FT_INTERNAL_DEBUG_H#include "sferrors.h"           /* must come before FT_INTERNAL_VALIDATE_H */#include FT_INTERNAL_VALIDATE_H#include FT_INTERNAL_STREAM_H#include "ttload.h"#include "ttcmap.h"  /*************************************************************************/  /*                                                                       */  /* The macro FT_COMPONENT is used in trace mode.  It is an implicit      */  /* parameter of the FT_TRACE() and FT_ERROR() macros, used to print/log  */  /* messages during execution.                                            */  /*                                                                       */#undef  FT_COMPONENT#define FT_COMPONENT  trace_ttcmap#define TT_PEEK_SHORT   FT_PEEK_SHORT#define TT_PEEK_USHORT  FT_PEEK_USHORT#define TT_PEEK_LONG    FT_PEEK_LONG#define TT_PEEK_ULONG   FT_PEEK_ULONG#define TT_NEXT_SHORT   FT_NEXT_SHORT#define TT_NEXT_USHORT  FT_NEXT_USHORT#define TT_NEXT_LONG    FT_NEXT_LONG#define TT_NEXT_ULONG   FT_NEXT_ULONG  FT_CALLBACK_DEF( FT_Error )  tt_cmap_init( TT_CMap   cmap,                FT_Byte*  table )  {    cmap->data = table;    return SFNT_Err_Ok;  }  /*************************************************************************/  /*************************************************************************/  /*****                                                               *****/  /*****                           FORMAT 0                            *****/  /*****                                                               *****/  /*************************************************************************/  /*************************************************************************/  /*************************************************************************/  /*                                                                       */  /* TABLE OVERVIEW                                                        */  /* --------------                                                        */  /*                                                                       */  /*   NAME        OFFSET         TYPE          DESCRIPTION                */  /*                                                                       */  /*   format      0              USHORT        must be 0                  */  /*   length      2              USHORT        table length in bytes      */  /*   language    4              USHORT        Mac language code          */  /*   glyph_ids   6              BYTE[256]     array of glyph indices     */  /*               262                                                     */  /*                                                                       */#ifdef TT_CONFIG_CMAP_FORMAT_0  FT_CALLBACK_DEF( FT_Error )  tt_cmap0_validate( FT_Byte*      table,                     FT_Validator  valid )  {    FT_Byte*  p      = table + 2;    FT_UInt   length = TT_NEXT_USHORT( p );    if ( table + length > valid->limit || length < 262 )      FT_INVALID_TOO_SHORT;    /* check glyph indices whenever necessary */    if ( valid->level >= FT_VALIDATE_TIGHT )    {      FT_UInt  n, idx;      p = table + 6;      for ( n = 0; n < 256; n++ )      {        idx = *p++;        if ( idx >= TT_VALID_GLYPH_COUNT( valid ) )          FT_INVALID_GLYPH_ID;      }    }    return SFNT_Err_Ok;  }  FT_CALLBACK_DEF( FT_UInt )  tt_cmap0_char_index( TT_CMap    cmap,                       FT_UInt32  char_code )  {    FT_Byte*  table = cmap->data;    return char_code < 256 ? table[6 + char_code] : 0;  }  FT_CALLBACK_DEF( FT_UInt )  tt_cmap0_char_next( TT_CMap     cmap,                      FT_UInt32  *pchar_code )  {    FT_Byte*   table    = cmap->data;    FT_UInt32  charcode = *pchar_code;    FT_UInt32  result   = 0;    FT_UInt    gindex   = 0;    table += 6;  /* go to glyph ids */    while ( ++charcode < 256 )    {      gindex = table[charcode];      if ( gindex != 0 )      {        result = charcode;        break;      }    }    *pchar_code = result;    return gindex;  }  FT_CALLBACK_DEF( FT_Error )  tt_cmap0_get_info( TT_CMap       cmap,                     TT_CMapInfo  *cmap_info )  {    FT_Byte*  p = cmap->data + 4;    cmap_info->language = (FT_ULong)TT_PEEK_USHORT( p );    return SFNT_Err_Ok;  }  FT_CALLBACK_TABLE_DEF  const TT_CMap_ClassRec  tt_cmap0_class_rec =  {    {      sizeof ( TT_CMapRec ),      (FT_CMap_InitFunc)     tt_cmap_init,      (FT_CMap_DoneFunc)     NULL,      (FT_CMap_CharIndexFunc)tt_cmap0_char_index,      (FT_CMap_CharNextFunc) tt_cmap0_char_next    },    0,    (TT_CMap_ValidateFunc)   tt_cmap0_validate,    (TT_CMap_Info_GetFunc)   tt_cmap0_get_info  };#endif /* TT_CONFIG_CMAP_FORMAT_0 */  /*************************************************************************/  /*************************************************************************/  /*****                                                               *****/  /*****                          FORMAT 2                             *****/  /*****                                                               *****/  /***** This is used for certain CJK encodings that encode text in a  *****/  /***** mixed 8/16 bits encoding along the following lines:           *****/  /*****                                                               *****/  /***** * Certain byte values correspond to an 8-bit character code   *****/  /*****   (typically in the range 0..127 for ASCII compatibility).    *****/  /*****                                                               *****/  /***** * Certain byte values signal the first byte of a 2-byte       *****/  /*****   character code (but these values are also valid as the      *****/  /*****   second byte of a 2-byte character).                         *****/  /*****                                                               *****/  /***** The following charmap lookup and iteration functions all      *****/  /***** assume that the value "charcode" correspond to following:     *****/  /*****                                                               *****/  /*****   - For one byte characters, "charcode" is simply the         *****/  /*****     character code.                                           *****/  /*****                                                               *****/  /*****   - For two byte characters, "charcode" is the 2-byte         *****/  /*****     character code in big endian format.  More exactly:       *****/  /*****                                                               *****/  /*****       (charcode >> 8)    is the first byte value              *****/  /*****       (charcode & 0xFF)  is the second byte value             *****/  /*****                                                               *****/  /***** Note that not all values of "charcode" are valid according    *****/  /***** to these rules, and the function moderately check the         *****/  /***** arguments.                                                    *****/  /*****                                                               *****/  /*************************************************************************/  /*************************************************************************/  /*************************************************************************/  /*                                                                       */  /* TABLE OVERVIEW                                                        */  /* --------------                                                        */  /*                                                                       */  /*   NAME        OFFSET         TYPE            DESCRIPTION              */  /*                                                                       */  /*   format      0              USHORT          must be 2                */  /*   length      2              USHORT          table length in bytes    */  /*   language    4              USHORT          Mac language code        */  /*   keys        6              USHORT[256]     sub-header keys          */  /*   subs        518            SUBHEAD[NSUBS]  sub-headers array        */  /*   glyph_ids   518+NSUB*8     USHORT[]        glyph id array           */  /*                                                                       */  /* The `keys' table is used to map charcode high-bytes to sub-headers.   */  /* The value of `NSUBS' is the number of sub-headers defined in the      */  /* table and is computed by finding the maximum of the `keys' table.     */  /*                                                                       */  /* Note that for any n, `keys[n]' is a byte offset within the `subs'     */  /* table, i.e., it is the corresponding sub-header index multiplied      */  /* by 8.                                                                 */  /*                                                                       */  /* Each sub-header has the following format:                             */  /*                                                                       */  /*   NAME        OFFSET      TYPE            DESCRIPTION                 */  /*                                                                       */  /*   first       0           USHORT          first valid low-byte        */  /*   count       2           USHORT          number of valid low-bytes   */  /*   delta       4           SHORT           see below                   */  /*   offset      6           USHORT          see below                   */  /*                                                                       */  /* A sub-header defines, for each high-byte, the range of valid          */  /* low-bytes within the charmap.  Note that the range defined by `first' */  /* and `count' must be completely included in the interval [0..255]      */  /* according to the specification.                                       */  /*                                                                       */  /* If a character code is contained within a given sub-header, then      */  /* mapping it to a glyph index is done as follows:                       */  /*                                                                       */  /* * The value of `offset' is read.  This is a _byte_ distance from the  */  /*   location of the `offset' field itself into a slice of the           */  /*   `glyph_ids' table.  Let's call it `slice' (it's a USHORT[] too).    */  /*                                                                       */  /* * The value `slice[char.lo - first]' is read.  If it is 0, there is   */  /*   no glyph for the charcode.  Otherwise, the value of `delta' is      */  /*   added to it (modulo 65536) to form a new glyph index.               */  /*                                                                       */  /* It is up to the validation routine to check that all offsets fall     */  /* within the glyph ids table (and not within the `subs' table itself or */  /* outside of the CMap).                                                 */  /*                                                                       */#ifdef TT_CONFIG_CMAP_FORMAT_2  FT_CALLBACK_DEF( FT_Error )  tt_cmap2_validate( FT_Byte*      table,                     FT_Validator  valid )  {    FT_Byte*  p      = table + 2;           /* skip format */    FT_UInt   length = TT_PEEK_USHORT( p );    FT_UInt   n, max_subs;    FT_Byte*  keys;                         /* keys table */    FT_Byte*  subs;                         /* sub-headers */    FT_Byte*  glyph_ids;                    /* glyph id array */    if ( table + length > valid->limit || length < 6 + 512 )      FT_INVALID_TOO_SHORT;    keys = table + 6;    /* parse keys to compute sub-headers count */    p        = keys;    max_subs = 0;    for ( n = 0; n < 256; n++ )    {      FT_UInt  idx = TT_NEXT_USHORT( p );      /* value must be multiple of 8 */      if ( valid->level >= FT_VALIDATE_PARANOID && ( idx & 7 ) != 0 )        FT_INVALID_DATA;      idx >>= 3;      if ( idx > max_subs )        max_subs = idx;    }    FT_ASSERT( p == table + 518 );    subs      = p;    glyph_ids = subs + (max_subs + 1) * 8;    if ( glyph_ids > valid->limit )      FT_INVALID_TOO_SHORT;    /* parse sub-headers */    for ( n = 0; n <= max_subs; n++ )    {      FT_UInt   first_code, code_count, offset;      FT_Int    delta;      FT_Byte*  ids;      first_code = TT_NEXT_USHORT( p );      code_count = TT_NEXT_USHORT( p );      delta      = TT_NEXT_SHORT( p );      offset     = TT_NEXT_USHORT( p );      /* check range within 0..255 */      if ( valid->level >= FT_VALIDATE_PARANOID )      {        if ( first_code >= 256 || first_code + code_count > 256 )          FT_INVALID_DATA;      }      /* check offset */      if ( offset != 0 )      {        ids = p - 2 + offset;        if ( ids < glyph_ids || ids + code_count*2 > table + length )          FT_INVALID_OFFSET;        /* check glyph ids */        if ( valid->level >= FT_VALIDATE_TIGHT )        {          FT_Byte*  limit = p + code_count * 2;          FT_UInt   idx;          for ( ; p < limit; )          {            idx = TT_NEXT_USHORT( p );            if ( idx != 0 )            {              idx = ( idx + delta ) & 0xFFFFU;              if ( idx >= TT_VALID_GLYPH_COUNT( valid ) )                FT_INVALID_GLYPH_ID;            }          }        }      }    }    return SFNT_Err_Ok;  }  /* return sub header corresponding to a given character code */  /* NULL on invalid charcode                                  */  static FT_Byte*  tt_cmap2_get_subheader( FT_Byte*   table,                          FT_UInt32  char_code )  {    FT_Byte*  result = NULL;    if ( char_code < 0x10000UL )    {      FT_UInt   char_lo = (FT_UInt)( char_code & 0xFF );      FT_UInt   char_hi = (FT_UInt)( char_code >> 8 );      FT_Byte*  p       = table + 6;    /* keys table */      FT_Byte*  subs    = table + 518;  /* subheaders table */      FT_Byte*  sub;      if ( char_hi == 0 )      {        /* an 8-bit character code -- we use subHeader 0 in this case */        /* to test whether the character code is in the charmap       */        /*                                                            */        sub = subs;  /* jump to first sub-header */        /* check that the sub-header for this byte is 0, which */        /* indicates that it's really a valid one-byte value   */        /* Otherwise, return 0                                 */        /*                                                     */        p += char_lo * 2;        if ( TT_PEEK_USHORT( p ) != 0 )          goto Exit;      }      else      {        /* a 16-bit character code */        /* jump to key entry  */        p  += char_hi * 2;        /* jump to sub-header */        sub = subs + ( FT_PAD_FLOOR( TT_PEEK_USHORT( p ), 8 ) );        /* check that the high byte isn't a valid one-byte value */

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -