1 /***************************************************************************/
   2 /*                                                                         */
   3 /*  ttsbit.c                                                               */
   4 /*                                                                         */
   5 /*    TrueType and OpenType embedded bitmap support (body).                */
   6 /*                                                                         */
   7 /*  Copyright 2005-2018 by                                                 */
   8 /*  David Turner, Robert Wilhelm, and Werner Lemberg.                      */
   9 /*                                                                         */
  10 /*  Copyright 2013 by Google, Inc.                                         */
  11 /*  Google Author(s): Behdad Esfahbod.                                     */
  12 /*                                                                         */
  13 /*  This file is part of the FreeType project, and may only be used,       */
  14 /*  modified, and distributed under the terms of the FreeType project      */
  15 /*  license, LICENSE.TXT.  By continuing to use, modify, or distribute     */
  16 /*  this file you indicate that you have read the license and              */
  17 /*  understand and accept it fully.                                        */
  18 /*                                                                         */
  19 /***************************************************************************/
  20 
  21 
  22 #include <ft2build.h>
  23 #include FT_INTERNAL_DEBUG_H
  24 #include FT_INTERNAL_STREAM_H
  25 #include FT_TRUETYPE_TAGS_H
  26 #include FT_BITMAP_H
  27 
  28 
  29 #ifdef TT_CONFIG_OPTION_EMBEDDED_BITMAPS
  30 
  31 #include "ttsbit.h"
  32 
  33 #include "sferrors.h"
  34 
  35 #include "ttmtx.h"
  36 #include "pngshim.h"
  37 
  38 
  39   /*************************************************************************/
  40   /*                                                                       */
  41   /* The macro FT_COMPONENT is used in trace mode.  It is an implicit      */
  42   /* parameter of the FT_TRACE() and FT_ERROR() macros, used to print/log  */
  43   /* messages during execution.                                            */
  44   /*                                                                       */
  45 #undef  FT_COMPONENT
  46 #define FT_COMPONENT  trace_ttsbit
  47 
  48 
  49   FT_LOCAL_DEF( FT_Error )
  50   tt_face_load_sbit( TT_Face    face,
  51                      FT_Stream  stream )
  52   {
  53     FT_Error  error;
  54     FT_ULong  table_size;
  55     FT_ULong  table_start;
  56 
  57 
  58     face->sbit_table       = NULL;
  59     face->sbit_table_size  = 0;
  60     face->sbit_table_type  = TT_SBIT_TABLE_TYPE_NONE;
  61     face->sbit_num_strikes = 0;
  62 
  63     error = face->goto_table( face, TTAG_CBLC, stream, &table_size );
  64     if ( !error )
  65       face->sbit_table_type = TT_SBIT_TABLE_TYPE_CBLC;
  66     else
  67     {
  68       error = face->goto_table( face, TTAG_EBLC, stream, &table_size );
  69       if ( error )
  70         error = face->goto_table( face, TTAG_bloc, stream, &table_size );
  71       if ( !error )
  72         face->sbit_table_type = TT_SBIT_TABLE_TYPE_EBLC;
  73     }
  74 
  75     if ( error )
  76     {
  77       error = face->goto_table( face, TTAG_sbix, stream, &table_size );
  78       if ( !error )
  79         face->sbit_table_type = TT_SBIT_TABLE_TYPE_SBIX;
  80     }
  81     if ( error )
  82       goto Exit;
  83 
  84     if ( table_size < 8 )
  85     {
  86       FT_ERROR(( "tt_face_load_sbit_strikes: table too short\n" ));
  87       error = FT_THROW( Invalid_File_Format );
  88       goto Exit;
  89     }
  90 
  91     table_start = FT_STREAM_POS();
  92 
  93     switch ( (FT_UInt)face->sbit_table_type )
  94     {
  95     case TT_SBIT_TABLE_TYPE_EBLC:
  96     case TT_SBIT_TABLE_TYPE_CBLC:
  97       {
  98         FT_Byte*  p;
  99         FT_Fixed  version;
 100         FT_ULong  num_strikes;
 101         FT_UInt   count;
 102 
 103 
 104         if ( FT_FRAME_EXTRACT( table_size, face->sbit_table ) )
 105           goto Exit;
 106 
 107         face->sbit_table_size = table_size;
 108 
 109         p = face->sbit_table;
 110 
 111         version     = FT_NEXT_LONG( p );
 112         num_strikes = FT_NEXT_ULONG( p );
 113 
 114         /* there's at least one font (FZShuSong-Z01, version 3)   */
 115         /* that uses the wrong byte order for the `version' field */
 116         if ( ( (FT_ULong)version & 0xFFFF0000UL ) != 0x00020000UL &&
 117              ( (FT_ULong)version & 0x0000FFFFUL ) != 0x00000200UL &&
 118              ( (FT_ULong)version & 0xFFFF0000UL ) != 0x00030000UL &&
 119              ( (FT_ULong)version & 0x0000FFFFUL ) != 0x00000300UL )
 120         {
 121           error = FT_THROW( Unknown_File_Format );
 122           goto Exit;
 123         }
 124 
 125         if ( num_strikes >= 0x10000UL )
 126         {
 127           error = FT_THROW( Invalid_File_Format );
 128           goto Exit;
 129         }
 130 
 131         /*
 132          *  Count the number of strikes available in the table.  We are a bit
 133          *  paranoid there and don't trust the data.
 134          */
 135         count = (FT_UInt)num_strikes;
 136         if ( 8 + 48UL * count > table_size )
 137           count = (FT_UInt)( ( table_size - 8 ) / 48 );
 138 
 139         face->sbit_num_strikes = count;
 140       }
 141       break;
 142 
 143     case TT_SBIT_TABLE_TYPE_SBIX:
 144       {
 145         FT_UShort  version;
 146         FT_UShort  flags;
 147         FT_ULong   num_strikes;
 148         FT_UInt    count;
 149 
 150 
 151         if ( FT_FRAME_ENTER( 8 ) )
 152           goto Exit;
 153 
 154         version     = FT_GET_USHORT();
 155         flags       = FT_GET_USHORT();
 156         num_strikes = FT_GET_ULONG();
 157 
 158         FT_FRAME_EXIT();
 159 
 160         if ( version < 1 )
 161         {
 162           error = FT_THROW( Unknown_File_Format );
 163           goto Exit;
 164         }
 165 
 166         /* Bit 0 must always be `1'.                            */
 167         /* Bit 1 controls the overlay of bitmaps with outlines. */
 168         /* All other bits should be zero.                       */
 169         if ( !( flags == 1 || flags == 3 ) ||
 170              num_strikes >= 0x10000UL      )
 171         {
 172           error = FT_THROW( Invalid_File_Format );
 173           goto Exit;
 174         }
 175 
 176         /* we currently don't support bit 1; however, it is better to */
 177         /* draw at least something...                                 */
 178         if ( flags == 3 )
 179           FT_TRACE1(( "tt_face_load_sbit_strikes:"
 180                       " sbix overlay not supported yet\n"
 181                       "                          "
 182                       " expect bad rendering results\n" ));
 183 
 184         /*
 185          *  Count the number of strikes available in the table.  We are a bit
 186          *  paranoid there and don't trust the data.
 187          */
 188         count = (FT_UInt)num_strikes;
 189         if ( 8 + 4UL * count > table_size )
 190           count = (FT_UInt)( ( table_size - 8 ) / 4 );
 191 
 192         if ( FT_STREAM_SEEK( FT_STREAM_POS() - 8 ) )
 193           goto Exit;
 194 
 195         face->sbit_table_size = 8 + count * 4;
 196         if ( FT_FRAME_EXTRACT( face->sbit_table_size, face->sbit_table ) )
 197           goto Exit;
 198 
 199         face->sbit_num_strikes = count;
 200       }
 201       break;
 202 
 203     default:
 204       /* we ignore unknown table formats */
 205       error = FT_THROW( Unknown_File_Format );
 206       break;
 207     }
 208 
 209     if ( !error )
 210       FT_TRACE3(( "tt_face_load_sbit_strikes: found %u strikes\n",
 211                   face->sbit_num_strikes ));
 212 
 213     face->ebdt_start = 0;
 214     face->ebdt_size  = 0;
 215 
 216     if ( face->sbit_table_type == TT_SBIT_TABLE_TYPE_SBIX )
 217     {
 218       /* the `sbix' table is self-contained; */
 219       /* it has no associated data table     */
 220       face->ebdt_start = table_start;
 221       face->ebdt_size  = table_size;
 222     }
 223     else if ( face->sbit_table_type != TT_SBIT_TABLE_TYPE_NONE )
 224     {
 225       FT_ULong  ebdt_size;
 226 
 227 
 228       error = face->goto_table( face, TTAG_CBDT, stream, &ebdt_size );
 229       if ( error )
 230         error = face->goto_table( face, TTAG_EBDT, stream, &ebdt_size );
 231       if ( error )
 232         error = face->goto_table( face, TTAG_bdat, stream, &ebdt_size );
 233 
 234       if ( !error )
 235       {
 236         face->ebdt_start = FT_STREAM_POS();
 237         face->ebdt_size  = ebdt_size;
 238       }
 239     }
 240 
 241     if ( !face->ebdt_size )
 242     {
 243       FT_TRACE2(( "tt_face_load_sbit_strikes:"
 244                   " no embedded bitmap data table found;\n"
 245                   "                          "
 246                   " resetting number of strikes to zero\n" ));
 247       face->sbit_num_strikes = 0;
 248     }
 249 
 250     return FT_Err_Ok;
 251 
 252   Exit:
 253     if ( error )
 254     {
 255       if ( face->sbit_table )
 256         FT_FRAME_RELEASE( face->sbit_table );
 257       face->sbit_table_size = 0;
 258       face->sbit_table_type = TT_SBIT_TABLE_TYPE_NONE;
 259     }
 260 
 261     return error;
 262   }
 263 
 264 
 265   FT_LOCAL_DEF( void )
 266   tt_face_free_sbit( TT_Face  face )
 267   {
 268     FT_Stream  stream = face->root.stream;
 269 
 270 
 271     FT_FRAME_RELEASE( face->sbit_table );
 272     face->sbit_table_size  = 0;
 273     face->sbit_table_type  = TT_SBIT_TABLE_TYPE_NONE;
 274     face->sbit_num_strikes = 0;
 275   }
 276 
 277 
 278   FT_LOCAL_DEF( FT_Error )
 279   tt_face_set_sbit_strike( TT_Face          face,
 280                            FT_Size_Request  req,
 281                            FT_ULong*        astrike_index )
 282   {
 283     return FT_Match_Size( (FT_Face)face, req, 0, astrike_index );
 284   }
 285 
 286 
 287   FT_LOCAL_DEF( FT_Error )
 288   tt_face_load_strike_metrics( TT_Face           face,
 289                                FT_ULong          strike_index,
 290                                FT_Size_Metrics*  metrics )
 291   {
 292     /* we have to test for the existence of `sbit_strike_map'    */
 293     /* because the function gets also used at the very beginning */
 294     /* to construct `sbit_strike_map' itself                     */
 295     if ( face->sbit_strike_map )
 296     {
 297       if ( strike_index >= (FT_ULong)face->root.num_fixed_sizes )
 298         return FT_THROW( Invalid_Argument );
 299 
 300       /* map to real index */
 301       strike_index = face->sbit_strike_map[strike_index];
 302     }
 303     else
 304     {
 305       if ( strike_index >= (FT_ULong)face->sbit_num_strikes )
 306         return FT_THROW( Invalid_Argument );
 307     }
 308 
 309     switch ( (FT_UInt)face->sbit_table_type )
 310     {
 311     case TT_SBIT_TABLE_TYPE_EBLC:
 312     case TT_SBIT_TABLE_TYPE_CBLC:
 313       {
 314         FT_Byte*  strike;
 315         FT_Char   max_before_bl;
 316         FT_Char   min_after_bl;
 317 
 318 
 319         strike = face->sbit_table + 8 + strike_index * 48;
 320 
 321         metrics->x_ppem = (FT_UShort)strike[44];
 322         metrics->y_ppem = (FT_UShort)strike[45];
 323 
 324         metrics->ascender  = (FT_Char)strike[16] * 64;  /* hori.ascender  */
 325         metrics->descender = (FT_Char)strike[17] * 64;  /* hori.descender */
 326 
 327         /* Due to fuzzy wording in the EBLC documentation, we find both */
 328         /* positive and negative values for `descender'.  Additionally, */
 329         /* many fonts have both `ascender' and `descender' set to zero  */
 330         /* (which is definitely wrong).  MS Windows simply ignores all  */
 331         /* those values...  For these reasons we apply some heuristics  */
 332         /* to get a reasonable, non-zero value for the height.          */
 333 
 334         max_before_bl = (FT_Char)strike[24];
 335         min_after_bl  = (FT_Char)strike[25];
 336 
 337         if ( metrics->descender > 0 )
 338         {
 339           /* compare sign of descender with `min_after_bl' */
 340           if ( min_after_bl < 0 )
 341             metrics->descender = -metrics->descender;
 342         }
 343 
 344         else if ( metrics->descender == 0 )
 345         {
 346           if ( metrics->ascender == 0 )
 347           {
 348             FT_TRACE2(( "tt_face_load_strike_metrics:"
 349                         " sanitizing invalid ascender and descender\n"
 350                         "                            "
 351                         " values for strike %d (%dppem, %dppem)\n",
 352                         strike_index,
 353                         metrics->x_ppem, metrics->y_ppem ));
 354 
 355             /* sanitize buggy ascender and descender values */
 356             if ( max_before_bl || min_after_bl )
 357             {
 358               metrics->ascender  = max_before_bl * 64;
 359               metrics->descender = min_after_bl * 64;
 360             }
 361             else
 362             {
 363               metrics->ascender  = metrics->y_ppem * 64;
 364               metrics->descender = 0;
 365             }
 366           }
 367         }
 368 
 369 #if 0
 370         else
 371           ; /* if we have a negative descender, simply use it */
 372 #endif
 373 
 374         metrics->height = metrics->ascender - metrics->descender;
 375         if ( metrics->height == 0 )
 376         {
 377           FT_TRACE2(( "tt_face_load_strike_metrics:"
 378                       " sanitizing invalid height value\n"
 379                       "                            "
 380                       " for strike (%d, %d)\n",
 381                       metrics->x_ppem, metrics->y_ppem ));
 382           metrics->height    = metrics->y_ppem * 64;
 383           metrics->descender = metrics->ascender - metrics->height;
 384         }
 385 
 386         /* Is this correct? */
 387         metrics->max_advance = ( (FT_Char)strike[22] + /* min_origin_SB  */
 388                                           strike[18] + /* max_width      */
 389                                  (FT_Char)strike[23]   /* min_advance_SB */
 390                                                      ) * 64;
 391 
 392         /* set the scale values (in 16.16 units) so advances */
 393         /* from the hmtx and vmtx table are scaled correctly */
 394         metrics->x_scale = FT_MulDiv( metrics->x_ppem,
 395                                       64 * 0x10000,
 396                                       face->header.Units_Per_EM );
 397         metrics->y_scale = FT_MulDiv( metrics->y_ppem,
 398                                       64 * 0x10000,
 399                                       face->header.Units_Per_EM );
 400 
 401         return FT_Err_Ok;
 402       }
 403 
 404     case TT_SBIT_TABLE_TYPE_SBIX:
 405       {
 406         FT_Stream       stream = face->root.stream;
 407         FT_UInt         offset;
 408         FT_UShort       upem, ppem, resolution;
 409         TT_HoriHeader  *hori;
 410         FT_Pos          ppem_; /* to reduce casts */
 411 
 412         FT_Error  error;
 413         FT_Byte*  p;
 414 
 415 
 416         p      = face->sbit_table + 8 + 4 * strike_index;
 417         offset = FT_NEXT_ULONG( p );
 418 
 419         if ( offset + 4 > face->ebdt_size )
 420           return FT_THROW( Invalid_File_Format );
 421 
 422         if ( FT_STREAM_SEEK( face->ebdt_start + offset ) ||
 423              FT_FRAME_ENTER( 4 )                         )
 424           return error;
 425 
 426         ppem       = FT_GET_USHORT();
 427         resolution = FT_GET_USHORT();
 428 
 429         FT_UNUSED( resolution ); /* What to do with this? */
 430 
 431         FT_FRAME_EXIT();
 432 
 433         upem = face->header.Units_Per_EM;
 434         hori = &face->horizontal;
 435 
 436         metrics->x_ppem = ppem;
 437         metrics->y_ppem = ppem;
 438 
 439         ppem_ = (FT_Pos)ppem;
 440 
 441         metrics->ascender =
 442           FT_MulDiv( hori->Ascender, ppem_ * 64, upem );
 443         metrics->descender =
 444           FT_MulDiv( hori->Descender, ppem_ * 64, upem );
 445         metrics->height =
 446           FT_MulDiv( hori->Ascender - hori->Descender + hori->Line_Gap,
 447                      ppem_ * 64, upem );
 448         metrics->max_advance =
 449           FT_MulDiv( hori->advance_Width_Max, ppem_ * 64, upem );
 450 
 451         /* set the scale values (in 16.16 units) so advances */
 452         /* from the hmtx and vmtx table are scaled correctly */
 453         metrics->x_scale = FT_MulDiv( metrics->x_ppem,
 454                                       64 * 0x10000,
 455                                       face->header.Units_Per_EM );
 456         metrics->y_scale = FT_MulDiv( metrics->y_ppem,
 457                                       64 * 0x10000,
 458                                       face->header.Units_Per_EM );
 459 
 460         return error;
 461       }
 462 
 463     default:
 464       return FT_THROW( Unknown_File_Format );
 465     }
 466   }
 467 
 468 
 469   typedef struct  TT_SBitDecoderRec_
 470   {
 471     TT_Face          face;
 472     FT_Stream        stream;
 473     FT_Bitmap*       bitmap;
 474     TT_SBit_Metrics  metrics;
 475     FT_Bool          metrics_loaded;
 476     FT_Bool          bitmap_allocated;
 477     FT_Byte          bit_depth;
 478 
 479     FT_ULong         ebdt_start;
 480     FT_ULong         ebdt_size;
 481 
 482     FT_ULong         strike_index_array;
 483     FT_ULong         strike_index_count;
 484     FT_Byte*         eblc_base;
 485     FT_Byte*         eblc_limit;
 486 
 487   } TT_SBitDecoderRec, *TT_SBitDecoder;
 488 
 489 
 490   static FT_Error
 491   tt_sbit_decoder_init( TT_SBitDecoder       decoder,
 492                         TT_Face              face,
 493                         FT_ULong             strike_index,
 494                         TT_SBit_MetricsRec*  metrics )
 495   {
 496     FT_Error   error  = FT_ERR( Table_Missing );
 497     FT_Stream  stream = face->root.stream;
 498 
 499 
 500     strike_index = face->sbit_strike_map[strike_index];
 501 
 502     if ( !face->ebdt_size )
 503       goto Exit;
 504     if ( FT_STREAM_SEEK( face->ebdt_start ) )
 505       goto Exit;
 506 
 507     decoder->face    = face;
 508     decoder->stream  = stream;
 509     decoder->bitmap  = &face->root.glyph->bitmap;
 510     decoder->metrics = metrics;
 511 
 512     decoder->metrics_loaded   = 0;
 513     decoder->bitmap_allocated = 0;
 514 
 515     decoder->ebdt_start = face->ebdt_start;
 516     decoder->ebdt_size  = face->ebdt_size;
 517 
 518     decoder->eblc_base  = face->sbit_table;
 519     decoder->eblc_limit = face->sbit_table + face->sbit_table_size;
 520 
 521     /* now find the strike corresponding to the index */
 522     {
 523       FT_Byte*  p;
 524 
 525 
 526       if ( 8 + 48 * strike_index + 3 * 4 + 34 + 1 > face->sbit_table_size )
 527       {
 528         error = FT_THROW( Invalid_File_Format );
 529         goto Exit;
 530       }
 531 
 532       p = decoder->eblc_base + 8 + 48 * strike_index;
 533 
 534       decoder->strike_index_array = FT_NEXT_ULONG( p );
 535       p                          += 4;
 536       decoder->strike_index_count = FT_NEXT_ULONG( p );
 537       p                          += 34;
 538       decoder->bit_depth          = *p;
 539 
 540       /* decoder->strike_index_array +                               */
 541       /*   8 * decoder->strike_index_count > face->sbit_table_size ? */
 542       if ( decoder->strike_index_array > face->sbit_table_size           ||
 543            decoder->strike_index_count >
 544              ( face->sbit_table_size - decoder->strike_index_array ) / 8 )
 545         error = FT_THROW( Invalid_File_Format );
 546     }
 547 
 548   Exit:
 549     return error;
 550   }
 551 
 552 
 553   static void
 554   tt_sbit_decoder_done( TT_SBitDecoder  decoder )
 555   {
 556     FT_UNUSED( decoder );
 557   }
 558 
 559 
 560   static FT_Error
 561   tt_sbit_decoder_alloc_bitmap( TT_SBitDecoder  decoder,
 562                                 FT_Bool         metrics_only )
 563   {
 564     FT_Error    error = FT_Err_Ok;
 565     FT_UInt     width, height;
 566     FT_Bitmap*  map = decoder->bitmap;
 567     FT_ULong    size;
 568 
 569 
 570     if ( !decoder->metrics_loaded )
 571     {
 572       error = FT_THROW( Invalid_Argument );
 573       goto Exit;
 574     }
 575 
 576     width  = decoder->metrics->width;
 577     height = decoder->metrics->height;
 578 
 579     map->width = width;
 580     map->rows  = height;
 581 
 582     switch ( decoder->bit_depth )
 583     {
 584     case 1:
 585       map->pixel_mode = FT_PIXEL_MODE_MONO;
 586       map->pitch      = (int)( ( map->width + 7 ) >> 3 );
 587       map->num_grays  = 2;
 588       break;
 589 
 590     case 2:
 591       map->pixel_mode = FT_PIXEL_MODE_GRAY2;
 592       map->pitch      = (int)( ( map->width + 3 ) >> 2 );
 593       map->num_grays  = 4;
 594       break;
 595 
 596     case 4:
 597       map->pixel_mode = FT_PIXEL_MODE_GRAY4;
 598       map->pitch      = (int)( ( map->width + 1 ) >> 1 );
 599       map->num_grays  = 16;
 600       break;
 601 
 602     case 8:
 603       map->pixel_mode = FT_PIXEL_MODE_GRAY;
 604       map->pitch      = (int)( map->width );
 605       map->num_grays  = 256;
 606       break;
 607 
 608     case 32:
 609       map->pixel_mode = FT_PIXEL_MODE_BGRA;
 610       map->pitch      = (int)( map->width * 4 );
 611       map->num_grays  = 256;
 612       break;
 613 
 614     default:
 615       error = FT_THROW( Invalid_File_Format );
 616       goto Exit;
 617     }
 618 
 619     size = map->rows * (FT_ULong)map->pitch;
 620 
 621     /* check that there is no empty image */
 622     if ( size == 0 )
 623       goto Exit;     /* exit successfully! */
 624 
 625     if ( metrics_only )
 626       goto Exit;     /* only metrics are requested */
 627 
 628     error = ft_glyphslot_alloc_bitmap( decoder->face->root.glyph, size );
 629     if ( error )
 630       goto Exit;
 631 
 632     decoder->bitmap_allocated = 1;
 633 
 634   Exit:
 635     return error;
 636   }
 637 
 638 
 639   static FT_Error
 640   tt_sbit_decoder_load_metrics( TT_SBitDecoder  decoder,
 641                                 FT_Byte*       *pp,
 642                                 FT_Byte*        limit,
 643                                 FT_Bool         big )
 644   {
 645     FT_Byte*         p       = *pp;
 646     TT_SBit_Metrics  metrics = decoder->metrics;
 647 
 648 
 649     if ( p + 5 > limit )
 650       goto Fail;
 651 
 652     metrics->height       = p[0];
 653     metrics->width        = p[1];
 654     metrics->horiBearingX = (FT_Char)p[2];
 655     metrics->horiBearingY = (FT_Char)p[3];
 656     metrics->horiAdvance  = p[4];
 657 
 658     p += 5;
 659     if ( big )
 660     {
 661       if ( p + 3 > limit )
 662         goto Fail;
 663 
 664       metrics->vertBearingX = (FT_Char)p[0];
 665       metrics->vertBearingY = (FT_Char)p[1];
 666       metrics->vertAdvance  = p[2];
 667 
 668       p += 3;
 669     }
 670     else
 671     {
 672       /* avoid uninitialized data in case there is no vertical info -- */
 673       metrics->vertBearingX = 0;
 674       metrics->vertBearingY = 0;
 675       metrics->vertAdvance  = 0;
 676     }
 677 
 678     decoder->metrics_loaded = 1;
 679     *pp = p;
 680     return FT_Err_Ok;
 681 
 682   Fail:
 683     FT_TRACE1(( "tt_sbit_decoder_load_metrics: broken table\n" ));
 684     return FT_THROW( Invalid_Argument );
 685   }
 686 
 687 
 688   /* forward declaration */
 689   static FT_Error
 690   tt_sbit_decoder_load_image( TT_SBitDecoder  decoder,
 691                               FT_UInt         glyph_index,
 692                               FT_Int          x_pos,
 693                               FT_Int          y_pos,
 694                               FT_UInt         recurse_count,
 695                               FT_Bool         metrics_only );
 696 
 697   typedef FT_Error  (*TT_SBitDecoder_LoadFunc)(
 698                       TT_SBitDecoder  decoder,
 699                       FT_Byte*        p,
 700                       FT_Byte*        plimit,
 701                       FT_Int          x_pos,
 702                       FT_Int          y_pos,
 703                       FT_UInt         recurse_count );
 704 
 705 
 706   static FT_Error
 707   tt_sbit_decoder_load_byte_aligned( TT_SBitDecoder  decoder,
 708                                      FT_Byte*        p,
 709                                      FT_Byte*        limit,
 710                                      FT_Int          x_pos,
 711                                      FT_Int          y_pos,
 712                                      FT_UInt         recurse_count )
 713   {
 714     FT_Error    error = FT_Err_Ok;
 715     FT_Byte*    line;
 716     FT_Int      pitch, width, height, line_bits, h;
 717     FT_UInt     bit_height, bit_width;
 718     FT_Bitmap*  bitmap;
 719 
 720     FT_UNUSED( recurse_count );
 721 
 722 
 723     /* check that we can write the glyph into the bitmap */
 724     bitmap     = decoder->bitmap;
 725     bit_width  = bitmap->width;
 726     bit_height = bitmap->rows;
 727     pitch      = bitmap->pitch;
 728     line       = bitmap->buffer;
 729 
 730     width  = decoder->metrics->width;
 731     height = decoder->metrics->height;
 732 
 733     line_bits = width * decoder->bit_depth;
 734 
 735     if ( x_pos < 0 || (FT_UInt)( x_pos + width ) > bit_width   ||
 736          y_pos < 0 || (FT_UInt)( y_pos + height ) > bit_height )
 737     {
 738       FT_TRACE1(( "tt_sbit_decoder_load_byte_aligned:"
 739                   " invalid bitmap dimensions\n" ));
 740       error = FT_THROW( Invalid_File_Format );
 741       goto Exit;
 742     }
 743 
 744     if ( p + ( ( line_bits + 7 ) >> 3 ) * height > limit )
 745     {
 746       FT_TRACE1(( "tt_sbit_decoder_load_byte_aligned: broken bitmap\n" ));
 747       error = FT_THROW( Invalid_File_Format );
 748       goto Exit;
 749     }
 750 
 751     /* now do the blit */
 752     line  += y_pos * pitch + ( x_pos >> 3 );
 753     x_pos &= 7;
 754 
 755     if ( x_pos == 0 )  /* the easy one */
 756     {
 757       for ( h = height; h > 0; h--, line += pitch )
 758       {
 759         FT_Byte*  pwrite = line;
 760         FT_Int    w;
 761 
 762 
 763         for ( w = line_bits; w >= 8; w -= 8 )
 764         {
 765           pwrite[0] = (FT_Byte)( pwrite[0] | *p++ );
 766           pwrite   += 1;
 767         }
 768 
 769         if ( w > 0 )
 770           pwrite[0] = (FT_Byte)( pwrite[0] | ( *p++ & ( 0xFF00U >> w ) ) );
 771       }
 772     }
 773     else  /* x_pos > 0 */
 774     {
 775       for ( h = height; h > 0; h--, line += pitch )
 776       {
 777         FT_Byte*  pwrite = line;
 778         FT_Int    w;
 779         FT_UInt   wval = 0;
 780 
 781 
 782         for ( w = line_bits; w >= 8; w -= 8 )
 783         {
 784           wval       = (FT_UInt)( wval | *p++ );
 785           pwrite[0]  = (FT_Byte)( pwrite[0] | ( wval >> x_pos ) );
 786           pwrite    += 1;
 787           wval     <<= 8;
 788         }
 789 
 790         if ( w > 0 )
 791           wval = (FT_UInt)( wval | ( *p++ & ( 0xFF00U >> w ) ) );
 792 
 793         /* all bits read and there are `x_pos + w' bits to be written */
 794 
 795         pwrite[0] = (FT_Byte)( pwrite[0] | ( wval >> x_pos ) );
 796 
 797         if ( x_pos + w > 8 )
 798         {
 799           pwrite++;
 800           wval     <<= 8;
 801           pwrite[0]  = (FT_Byte)( pwrite[0] | ( wval >> x_pos ) );
 802         }
 803       }
 804     }
 805 
 806   Exit:
 807     if ( !error )
 808       FT_TRACE3(( "tt_sbit_decoder_load_byte_aligned: loaded\n" ));
 809     return error;
 810   }
 811 
 812 
 813   /*
 814    * Load a bit-aligned bitmap (with pointer `p') into a line-aligned bitmap
 815    * (with pointer `pwrite').  In the example below, the width is 3 pixel,
 816    * and `x_pos' is 1 pixel.
 817    *
 818    *       p                               p+1
 819    *     |                               |                               |
 820    *     | 7   6   5   4   3   2   1   0 | 7   6   5   4   3   2   1   0 |...
 821    *     |                               |                               |
 822    *       +-------+   +-------+   +-------+ ...
 823    *           .           .           .
 824    *           .           .           .
 825    *           v           .           .
 826    *       +-------+       .           .
 827    * |                               | .
 828    * | 7   6   5   4   3   2   1   0 | .
 829    * |                               | .
 830    *   pwrite              .           .
 831    *                       .           .
 832    *                       v           .
 833    *                   +-------+       .
 834    *             |                               |
 835    *             | 7   6   5   4   3   2   1   0 |
 836    *             |                               |
 837    *               pwrite+1            .
 838    *                                   .
 839    *                                   v
 840    *                               +-------+
 841    *                         |                               |
 842    *                         | 7   6   5   4   3   2   1   0 |
 843    *                         |                               |
 844    *                           pwrite+2
 845    *
 846    */
 847 
 848   static FT_Error
 849   tt_sbit_decoder_load_bit_aligned( TT_SBitDecoder  decoder,
 850                                     FT_Byte*        p,
 851                                     FT_Byte*        limit,
 852                                     FT_Int          x_pos,
 853                                     FT_Int          y_pos,
 854                                     FT_UInt         recurse_count )
 855   {
 856     FT_Error    error = FT_Err_Ok;
 857     FT_Byte*    line;
 858     FT_Int      pitch, width, height, line_bits, h, nbits;
 859     FT_UInt     bit_height, bit_width;
 860     FT_Bitmap*  bitmap;
 861     FT_UShort   rval;
 862 
 863     FT_UNUSED( recurse_count );
 864 
 865 
 866     /* check that we can write the glyph into the bitmap */
 867     bitmap     = decoder->bitmap;
 868     bit_width  = bitmap->width;
 869     bit_height = bitmap->rows;
 870     pitch      = bitmap->pitch;
 871     line       = bitmap->buffer;
 872 
 873     width  = decoder->metrics->width;
 874     height = decoder->metrics->height;
 875 
 876     line_bits = width * decoder->bit_depth;
 877 
 878     if ( x_pos < 0 || (FT_UInt)( x_pos + width ) > bit_width   ||
 879          y_pos < 0 || (FT_UInt)( y_pos + height ) > bit_height )
 880     {
 881       FT_TRACE1(( "tt_sbit_decoder_load_bit_aligned:"
 882                   " invalid bitmap dimensions\n" ));
 883       error = FT_THROW( Invalid_File_Format );
 884       goto Exit;
 885     }
 886 
 887     if ( p + ( ( line_bits * height + 7 ) >> 3 ) > limit )
 888     {
 889       FT_TRACE1(( "tt_sbit_decoder_load_bit_aligned: broken bitmap\n" ));
 890       error = FT_THROW( Invalid_File_Format );
 891       goto Exit;
 892     }
 893 
 894     if ( !line_bits || !height )
 895     {
 896       /* nothing to do */
 897       goto Exit;
 898     }
 899 
 900     /* now do the blit */
 901 
 902     /* adjust `line' to point to the first byte of the bitmap */
 903     line  += y_pos * pitch + ( x_pos >> 3 );
 904     x_pos &= 7;
 905 
 906     /* the higher byte of `rval' is used as a buffer */
 907     rval  = 0;
 908     nbits = 0;
 909 
 910     for ( h = height; h > 0; h--, line += pitch )
 911     {
 912       FT_Byte*  pwrite = line;
 913       FT_Int    w      = line_bits;
 914 
 915 
 916       /* handle initial byte (in target bitmap) specially if necessary */
 917       if ( x_pos )
 918       {
 919         w = ( line_bits < 8 - x_pos ) ? line_bits : 8 - x_pos;
 920 
 921         if ( h == height )
 922         {
 923           rval  = *p++;
 924           nbits = x_pos;
 925         }
 926         else if ( nbits < w )
 927         {
 928           if ( p < limit )
 929             rval |= *p++;
 930           nbits += 8 - w;
 931         }
 932         else
 933         {
 934           rval  >>= 8;
 935           nbits  -= w;
 936         }
 937 
 938         *pwrite++ |= ( ( rval >> nbits ) & 0xFF ) &
 939                      ( ~( 0xFFU << w ) << ( 8 - w - x_pos ) );
 940         rval     <<= 8;
 941 
 942         w = line_bits - w;
 943       }
 944 
 945       /* handle medial bytes */
 946       for ( ; w >= 8; w -= 8 )
 947       {
 948         rval      |= *p++;
 949         *pwrite++ |= ( rval >> nbits ) & 0xFF;
 950 
 951         rval <<= 8;
 952       }
 953 
 954       /* handle final byte if necessary */
 955       if ( w > 0 )
 956       {
 957         if ( nbits < w )
 958         {
 959           if ( p < limit )
 960             rval |= *p++;
 961           *pwrite |= ( ( rval >> nbits ) & 0xFF ) & ( 0xFF00U >> w );
 962           nbits   += 8 - w;
 963 
 964           rval <<= 8;
 965         }
 966         else
 967         {
 968           *pwrite |= ( ( rval >> nbits ) & 0xFF ) & ( 0xFF00U >> w );
 969           nbits   -= w;
 970         }
 971       }
 972     }
 973 
 974   Exit:
 975     if ( !error )
 976       FT_TRACE3(( "tt_sbit_decoder_load_bit_aligned: loaded\n" ));
 977     return error;
 978   }
 979 
 980 
 981   static FT_Error
 982   tt_sbit_decoder_load_compound( TT_SBitDecoder  decoder,
 983                                  FT_Byte*        p,
 984                                  FT_Byte*        limit,
 985                                  FT_Int          x_pos,
 986                                  FT_Int          y_pos,
 987                                  FT_UInt         recurse_count )
 988   {
 989     FT_Error  error = FT_Err_Ok;
 990     FT_UInt   num_components, nn;
 991 
 992     FT_Char  horiBearingX = (FT_Char)decoder->metrics->horiBearingX;
 993     FT_Char  horiBearingY = (FT_Char)decoder->metrics->horiBearingY;
 994     FT_Byte  horiAdvance  = (FT_Byte)decoder->metrics->horiAdvance;
 995     FT_Char  vertBearingX = (FT_Char)decoder->metrics->vertBearingX;
 996     FT_Char  vertBearingY = (FT_Char)decoder->metrics->vertBearingY;
 997     FT_Byte  vertAdvance  = (FT_Byte)decoder->metrics->vertAdvance;
 998 
 999 
1000     if ( p + 2 > limit )
1001       goto Fail;
1002 
1003     num_components = FT_NEXT_USHORT( p );
1004     if ( p + 4 * num_components > limit )
1005     {
1006       FT_TRACE1(( "tt_sbit_decoder_load_compound: broken table\n" ));
1007       goto Fail;
1008     }
1009 
1010     FT_TRACE3(( "tt_sbit_decoder_load_compound: loading %d component%s\n",
1011                 num_components,
1012                 num_components == 1 ? "" : "s" ));
1013 
1014     for ( nn = 0; nn < num_components; nn++ )
1015     {
1016       FT_UInt  gindex = FT_NEXT_USHORT( p );
1017       FT_Byte  dx     = FT_NEXT_BYTE( p );
1018       FT_Byte  dy     = FT_NEXT_BYTE( p );
1019 
1020 
1021       /* NB: a recursive call */
1022       error = tt_sbit_decoder_load_image( decoder,
1023                                           gindex,
1024                                           x_pos + dx,
1025                                           y_pos + dy,
1026                                           recurse_count + 1,
1027                                           /* request full bitmap image */
1028                                           FALSE );
1029       if ( error )
1030         break;
1031     }
1032 
1033     FT_TRACE3(( "tt_sbit_decoder_load_compound: done\n" ));
1034 
1035     decoder->metrics->horiBearingX = horiBearingX;
1036     decoder->metrics->horiBearingY = horiBearingY;
1037     decoder->metrics->horiAdvance  = horiAdvance;
1038     decoder->metrics->vertBearingX = vertBearingX;
1039     decoder->metrics->vertBearingY = vertBearingY;
1040     decoder->metrics->vertAdvance  = vertAdvance;
1041     decoder->metrics->width        = (FT_Byte)decoder->bitmap->width;
1042     decoder->metrics->height       = (FT_Byte)decoder->bitmap->rows;
1043 
1044   Exit:
1045     return error;
1046 
1047   Fail:
1048     error = FT_THROW( Invalid_File_Format );
1049     goto Exit;
1050   }
1051 
1052 
1053 #ifdef FT_CONFIG_OPTION_USE_PNG
1054 
1055   static FT_Error
1056   tt_sbit_decoder_load_png( TT_SBitDecoder  decoder,
1057                             FT_Byte*        p,
1058                             FT_Byte*        limit,
1059                             FT_Int          x_pos,
1060                             FT_Int          y_pos,
1061                             FT_UInt         recurse_count )
1062   {
1063     FT_Error  error = FT_Err_Ok;
1064     FT_ULong  png_len;
1065 
1066     FT_UNUSED( recurse_count );
1067 
1068 
1069     if ( limit - p < 4 )
1070     {
1071       FT_TRACE1(( "tt_sbit_decoder_load_png: broken bitmap\n" ));
1072       error = FT_THROW( Invalid_File_Format );
1073       goto Exit;
1074     }
1075 
1076     png_len = FT_NEXT_ULONG( p );
1077     if ( (FT_ULong)( limit - p ) < png_len )
1078     {
1079       FT_TRACE1(( "tt_sbit_decoder_load_png: broken bitmap\n" ));
1080       error = FT_THROW( Invalid_File_Format );
1081       goto Exit;
1082     }
1083 
1084     error = Load_SBit_Png( decoder->face->root.glyph,
1085                            x_pos,
1086                            y_pos,
1087                            decoder->bit_depth,
1088                            decoder->metrics,
1089                            decoder->stream->memory,
1090                            p,
1091                            png_len,
1092                            FALSE,
1093                            FALSE );
1094 
1095   Exit:
1096     if ( !error )
1097       FT_TRACE3(( "tt_sbit_decoder_load_png: loaded\n" ));
1098     return error;
1099   }
1100 
1101 #endif /* FT_CONFIG_OPTION_USE_PNG */
1102 
1103 
1104   static FT_Error
1105   tt_sbit_decoder_load_bitmap( TT_SBitDecoder  decoder,
1106                                FT_UInt         glyph_format,
1107                                FT_ULong        glyph_start,
1108                                FT_ULong        glyph_size,
1109                                FT_Int          x_pos,
1110                                FT_Int          y_pos,
1111                                FT_UInt         recurse_count,
1112                                FT_Bool         metrics_only )
1113   {
1114     FT_Error   error;
1115     FT_Stream  stream = decoder->stream;
1116     FT_Byte*   p;
1117     FT_Byte*   p_limit;
1118     FT_Byte*   data;
1119 
1120 
1121     /* seek into the EBDT table now */
1122     if ( !glyph_size                                   ||
1123          glyph_start + glyph_size > decoder->ebdt_size )
1124     {
1125       error = FT_THROW( Invalid_Argument );
1126       goto Exit;
1127     }
1128 
1129     if ( FT_STREAM_SEEK( decoder->ebdt_start + glyph_start ) ||
1130          FT_FRAME_EXTRACT( glyph_size, data )                )
1131       goto Exit;
1132 
1133     p       = data;
1134     p_limit = p + glyph_size;
1135 
1136     /* read the data, depending on the glyph format */
1137     switch ( glyph_format )
1138     {
1139     case 1:
1140     case 2:
1141     case 8:
1142     case 17:
1143       error = tt_sbit_decoder_load_metrics( decoder, &p, p_limit, 0 );
1144       break;
1145 
1146     case 6:
1147     case 7:
1148     case 9:
1149     case 18:
1150       error = tt_sbit_decoder_load_metrics( decoder, &p, p_limit, 1 );
1151       break;
1152 
1153     default:
1154       error = FT_Err_Ok;
1155     }
1156 
1157     if ( error )
1158       goto Fail;
1159 
1160     {
1161       TT_SBitDecoder_LoadFunc  loader;
1162 
1163 
1164       switch ( glyph_format )
1165       {
1166       case 1:
1167       case 6:
1168         loader = tt_sbit_decoder_load_byte_aligned;
1169         break;
1170 
1171       case 2:
1172       case 7:
1173         {
1174           /* Don't trust `glyph_format'.  For example, Apple's main Korean */
1175           /* system font, `AppleMyungJo.ttf' (version 7.0d2e6), uses glyph */
1176           /* format 7, but the data is format 6.  We check whether we have */
1177           /* an excessive number of bytes in the image: If it is equal to  */
1178           /* the value for a byte-aligned glyph, use the other loading     */
1179           /* routine.                                                      */
1180           /*                                                               */
1181           /* Note that for some (width,height) combinations, where the     */
1182           /* width is not a multiple of 8, the sizes for bit- and          */
1183           /* byte-aligned data are equal, for example (7,7) or (15,6).  We */
1184           /* then prefer what `glyph_format' specifies.                    */
1185 
1186           FT_UInt  width  = decoder->metrics->width;
1187           FT_UInt  height = decoder->metrics->height;
1188 
1189           FT_UInt  bit_size  = ( width * height + 7 ) >> 3;
1190           FT_UInt  byte_size = height * ( ( width + 7 ) >> 3 );
1191 
1192 
1193           if ( bit_size < byte_size                  &&
1194                byte_size == (FT_UInt)( p_limit - p ) )
1195             loader = tt_sbit_decoder_load_byte_aligned;
1196           else
1197             loader = tt_sbit_decoder_load_bit_aligned;
1198         }
1199         break;
1200 
1201       case 5:
1202         loader = tt_sbit_decoder_load_bit_aligned;
1203         break;
1204 
1205       case 8:
1206         if ( p + 1 > p_limit )
1207           goto Fail;
1208 
1209         p += 1;  /* skip padding */
1210         /* fall-through */
1211 
1212       case 9:
1213         loader = tt_sbit_decoder_load_compound;
1214         break;
1215 
1216       case 17: /* small metrics, PNG image data   */
1217       case 18: /* big metrics, PNG image data     */
1218       case 19: /* metrics in EBLC, PNG image data */
1219 #ifdef FT_CONFIG_OPTION_USE_PNG
1220         loader = tt_sbit_decoder_load_png;
1221         break;
1222 #else
1223         error = FT_THROW( Unimplemented_Feature );
1224         goto Fail;
1225 #endif /* FT_CONFIG_OPTION_USE_PNG */
1226 
1227       default:
1228         error = FT_THROW( Invalid_Table );
1229         goto Fail;
1230       }
1231 
1232       if ( !decoder->bitmap_allocated )
1233       {
1234         error = tt_sbit_decoder_alloc_bitmap( decoder, metrics_only );
1235 
1236         if ( error )
1237           goto Fail;
1238       }
1239 
1240       if ( metrics_only )
1241         goto Fail; /* this is not an error */
1242 
1243       error = loader( decoder, p, p_limit, x_pos, y_pos, recurse_count );
1244     }
1245 
1246   Fail:
1247     FT_FRAME_RELEASE( data );
1248 
1249   Exit:
1250     return error;
1251   }
1252 
1253 
1254   static FT_Error
1255   tt_sbit_decoder_load_image( TT_SBitDecoder  decoder,
1256                               FT_UInt         glyph_index,
1257                               FT_Int          x_pos,
1258                               FT_Int          y_pos,
1259                               FT_UInt         recurse_count,
1260                               FT_Bool         metrics_only )
1261   {
1262     FT_Byte*  p          = decoder->eblc_base + decoder->strike_index_array;
1263     FT_Byte*  p_limit    = decoder->eblc_limit;
1264     FT_ULong  num_ranges = decoder->strike_index_count;
1265     FT_UInt   start, end, index_format, image_format;
1266     FT_ULong  image_start = 0, image_end = 0, image_offset;
1267 
1268 
1269     /* arbitrary recursion limit */
1270     if ( recurse_count > 100 )
1271     {
1272       FT_TRACE4(( "tt_sbit_decoder_load_image:"
1273                   " recursion depth exceeded\n" ));
1274       goto Failure;
1275     }
1276 
1277 
1278     /* First, we find the correct strike range that applies to this */
1279     /* glyph index.                                                 */
1280     for ( ; num_ranges > 0; num_ranges-- )
1281     {
1282       start = FT_NEXT_USHORT( p );
1283       end   = FT_NEXT_USHORT( p );
1284 
1285       if ( glyph_index >= start && glyph_index <= end )
1286         goto FoundRange;
1287 
1288       p += 4;  /* ignore index offset */
1289     }
1290     goto NoBitmap;
1291 
1292   FoundRange:
1293     image_offset = FT_NEXT_ULONG( p );
1294 
1295     /* overflow check */
1296     p = decoder->eblc_base + decoder->strike_index_array;
1297     if ( image_offset > (FT_ULong)( p_limit - p ) )
1298       goto Failure;
1299 
1300     p += image_offset;
1301     if ( p + 8 > p_limit )
1302       goto NoBitmap;
1303 
1304     /* now find the glyph's location and extend within the ebdt table */
1305     index_format = FT_NEXT_USHORT( p );
1306     image_format = FT_NEXT_USHORT( p );
1307     image_offset = FT_NEXT_ULONG ( p );
1308 
1309     switch ( index_format )
1310     {
1311     case 1: /* 4-byte offsets relative to `image_offset' */
1312       p += 4 * ( glyph_index - start );
1313       if ( p + 8 > p_limit )
1314         goto NoBitmap;
1315 
1316       image_start = FT_NEXT_ULONG( p );
1317       image_end   = FT_NEXT_ULONG( p );
1318 
1319       if ( image_start == image_end )  /* missing glyph */
1320         goto NoBitmap;
1321       break;
1322 
1323     case 2: /* big metrics, constant image size */
1324       {
1325         FT_ULong  image_size;
1326 
1327 
1328         if ( p + 12 > p_limit )
1329           goto NoBitmap;
1330 
1331         image_size = FT_NEXT_ULONG( p );
1332 
1333         if ( tt_sbit_decoder_load_metrics( decoder, &p, p_limit, 1 ) )
1334           goto NoBitmap;
1335 
1336         image_start = image_size * ( glyph_index - start );
1337         image_end   = image_start + image_size;
1338       }
1339       break;
1340 
1341     case 3: /* 2-byte offsets relative to 'image_offset' */
1342       p += 2 * ( glyph_index - start );
1343       if ( p + 4 > p_limit )
1344         goto NoBitmap;
1345 
1346       image_start = FT_NEXT_USHORT( p );
1347       image_end   = FT_NEXT_USHORT( p );
1348 
1349       if ( image_start == image_end )  /* missing glyph */
1350         goto NoBitmap;
1351       break;
1352 
1353     case 4: /* sparse glyph array with (glyph,offset) pairs */
1354       {
1355         FT_ULong  mm, num_glyphs;
1356 
1357 
1358         if ( p + 4 > p_limit )
1359           goto NoBitmap;
1360 
1361         num_glyphs = FT_NEXT_ULONG( p );
1362 
1363         /* overflow check for p + ( num_glyphs + 1 ) * 4 */
1364         if ( p + 4 > p_limit                                         ||
1365              num_glyphs > (FT_ULong)( ( ( p_limit - p ) >> 2 ) - 1 ) )
1366           goto NoBitmap;
1367 
1368         for ( mm = 0; mm < num_glyphs; mm++ )
1369         {
1370           FT_UInt  gindex = FT_NEXT_USHORT( p );
1371 
1372 
1373           if ( gindex == glyph_index )
1374           {
1375             image_start = FT_NEXT_USHORT( p );
1376             p          += 2;
1377             image_end   = FT_PEEK_USHORT( p );
1378             break;
1379           }
1380           p += 2;
1381         }
1382 
1383         if ( mm >= num_glyphs )
1384           goto NoBitmap;
1385       }
1386       break;
1387 
1388     case 5: /* constant metrics with sparse glyph codes */
1389     case 19:
1390       {
1391         FT_ULong  image_size, mm, num_glyphs;
1392 
1393 
1394         if ( p + 16 > p_limit )
1395           goto NoBitmap;
1396 
1397         image_size = FT_NEXT_ULONG( p );
1398 
1399         if ( tt_sbit_decoder_load_metrics( decoder, &p, p_limit, 1 ) )
1400           goto NoBitmap;
1401 
1402         num_glyphs = FT_NEXT_ULONG( p );
1403 
1404         /* overflow check for p + 2 * num_glyphs */
1405         if ( num_glyphs > (FT_ULong)( ( p_limit - p ) >> 1 ) )
1406           goto NoBitmap;
1407 
1408         for ( mm = 0; mm < num_glyphs; mm++ )
1409         {
1410           FT_UInt  gindex = FT_NEXT_USHORT( p );
1411 
1412 
1413           if ( gindex == glyph_index )
1414             break;
1415         }
1416 
1417         if ( mm >= num_glyphs )
1418           goto NoBitmap;
1419 
1420         image_start = image_size * mm;
1421         image_end   = image_start + image_size;
1422       }
1423       break;
1424 
1425     default:
1426       goto NoBitmap;
1427     }
1428 
1429     if ( image_start > image_end )
1430       goto NoBitmap;
1431 
1432     image_end  -= image_start;
1433     image_start = image_offset + image_start;
1434 
1435     FT_TRACE3(( "tt_sbit_decoder_load_image:"
1436                 " found sbit (format %d) for glyph index %d\n",
1437                 image_format, glyph_index ));
1438 
1439     return tt_sbit_decoder_load_bitmap( decoder,
1440                                         image_format,
1441                                         image_start,
1442                                         image_end,
1443                                         x_pos,
1444                                         y_pos,
1445                                         recurse_count,
1446                                         metrics_only );
1447 
1448   Failure:
1449     return FT_THROW( Invalid_Table );
1450 
1451   NoBitmap:
1452     if ( recurse_count )
1453     {
1454       FT_TRACE4(( "tt_sbit_decoder_load_image:"
1455                   " missing subglyph sbit with glyph index %d\n",
1456                   glyph_index ));
1457       return FT_THROW( Invalid_Composite );
1458     }
1459 
1460     FT_TRACE4(( "tt_sbit_decoder_load_image:"
1461                 " no sbit found for glyph index %d\n", glyph_index ));
1462     return FT_THROW( Missing_Bitmap );
1463   }
1464 
1465 
1466   static FT_Error
1467   tt_face_load_sbix_image( TT_Face              face,
1468                            FT_ULong             strike_index,
1469                            FT_UInt              glyph_index,
1470                            FT_Stream            stream,
1471                            FT_Bitmap           *map,
1472                            TT_SBit_MetricsRec  *metrics,
1473                            FT_Bool              metrics_only )
1474   {
1475     FT_UInt   strike_offset, glyph_start, glyph_end;
1476     FT_Int    originOffsetX, originOffsetY;
1477     FT_Tag    graphicType;
1478     FT_Int    recurse_depth = 0;
1479 
1480     FT_Error  error;
1481     FT_Byte*  p;
1482 
1483     FT_UNUSED( map );
1484 #ifndef FT_CONFIG_OPTION_USE_PNG
1485     FT_UNUSED( metrics_only );
1486 #endif
1487 
1488 
1489     strike_index = face->sbit_strike_map[strike_index];
1490 
1491     metrics->width  = 0;
1492     metrics->height = 0;
1493 
1494     p = face->sbit_table + 8 + 4 * strike_index;
1495     strike_offset = FT_NEXT_ULONG( p );
1496 
1497   retry:
1498     if ( glyph_index > (FT_UInt)face->root.num_glyphs )
1499       return FT_THROW( Invalid_Argument );
1500 
1501     if ( strike_offset >= face->ebdt_size                          ||
1502          face->ebdt_size - strike_offset < 4 + glyph_index * 4 + 8 )
1503       return FT_THROW( Invalid_File_Format );
1504 
1505     if ( FT_STREAM_SEEK( face->ebdt_start  +
1506                          strike_offset + 4 +
1507                          glyph_index * 4   ) ||
1508          FT_FRAME_ENTER( 8 )                 )
1509       return error;
1510 
1511     glyph_start = FT_GET_ULONG();
1512     glyph_end   = FT_GET_ULONG();
1513 
1514     FT_FRAME_EXIT();
1515 
1516     if ( glyph_start == glyph_end )
1517       return FT_THROW( Missing_Bitmap );
1518     if ( glyph_start > glyph_end                     ||
1519          glyph_end - glyph_start < 8                 ||
1520          face->ebdt_size - strike_offset < glyph_end )
1521       return FT_THROW( Invalid_File_Format );
1522 
1523     if ( FT_STREAM_SEEK( face->ebdt_start + strike_offset + glyph_start ) ||
1524          FT_FRAME_ENTER( glyph_end - glyph_start )                        )
1525       return error;
1526 
1527     originOffsetX = FT_GET_SHORT();
1528     originOffsetY = FT_GET_SHORT();
1529 
1530     graphicType = FT_GET_TAG4();
1531 
1532     switch ( graphicType )
1533     {
1534     case FT_MAKE_TAG( 'd', 'u', 'p', 'e' ):
1535       if ( recurse_depth < 4 )
1536       {
1537         glyph_index = FT_GET_USHORT();
1538         FT_FRAME_EXIT();
1539         recurse_depth++;
1540         goto retry;
1541       }
1542       error = FT_THROW( Invalid_File_Format );
1543       break;
1544 
1545     case FT_MAKE_TAG( 'p', 'n', 'g', ' ' ):
1546 #ifdef FT_CONFIG_OPTION_USE_PNG
1547       error = Load_SBit_Png( face->root.glyph,
1548                              0,
1549                              0,
1550                              32,
1551                              metrics,
1552                              stream->memory,
1553                              stream->cursor,
1554                              glyph_end - glyph_start - 8,
1555                              TRUE,
1556                              metrics_only );
1557 #else
1558       error = FT_THROW( Unimplemented_Feature );
1559 #endif
1560       break;
1561 
1562     case FT_MAKE_TAG( 'j', 'p', 'g', ' ' ):
1563     case FT_MAKE_TAG( 't', 'i', 'f', 'f' ):
1564     case FT_MAKE_TAG( 'r', 'g', 'b', 'l' ): /* used on iOS 7.1 */
1565       error = FT_THROW( Unknown_File_Format );
1566       break;
1567 
1568     default:
1569       error = FT_THROW( Unimplemented_Feature );
1570       break;
1571     }
1572 
1573     FT_FRAME_EXIT();
1574 
1575     if ( !error )
1576     {
1577       FT_Short   abearing;
1578       FT_UShort  aadvance;
1579 
1580 
1581       tt_face_get_metrics( face, FALSE, glyph_index, &abearing, &aadvance );
1582 
1583       metrics->horiBearingX = (FT_Short)originOffsetX;
1584       metrics->horiBearingY = (FT_Short)( -originOffsetY + metrics->height );
1585       metrics->horiAdvance  = (FT_UShort)( aadvance *
1586                                            face->root.size->metrics.x_ppem /
1587                                            face->header.Units_Per_EM );
1588     }
1589 
1590     return error;
1591   }
1592 
1593   FT_LOCAL( FT_Error )
1594   tt_face_load_sbit_image( TT_Face              face,
1595                            FT_ULong             strike_index,
1596                            FT_UInt              glyph_index,
1597                            FT_UInt              load_flags,
1598                            FT_Stream            stream,
1599                            FT_Bitmap           *map,
1600                            TT_SBit_MetricsRec  *metrics )
1601   {
1602     FT_Error  error = FT_Err_Ok;
1603 
1604 
1605     switch ( (FT_UInt)face->sbit_table_type )
1606     {
1607     case TT_SBIT_TABLE_TYPE_EBLC:
1608     case TT_SBIT_TABLE_TYPE_CBLC:
1609       {
1610         TT_SBitDecoderRec  decoder[1];
1611 
1612 
1613         error = tt_sbit_decoder_init( decoder, face, strike_index, metrics );
1614         if ( !error )
1615         {
1616           error = tt_sbit_decoder_load_image(
1617                     decoder,
1618                     glyph_index,
1619                     0,
1620                     0,
1621                     0,
1622                     ( load_flags & FT_LOAD_BITMAP_METRICS_ONLY ) != 0 );
1623           tt_sbit_decoder_done( decoder );
1624         }
1625       }
1626       break;
1627 
1628     case TT_SBIT_TABLE_TYPE_SBIX:
1629       error = tt_face_load_sbix_image(
1630                 face,
1631                 strike_index,
1632                 glyph_index,
1633                 stream,
1634                 map,
1635                 metrics,
1636                 ( load_flags & FT_LOAD_BITMAP_METRICS_ONLY ) != 0 );
1637       break;
1638 
1639     default:
1640       error = FT_THROW( Unknown_File_Format );
1641       break;
1642     }
1643 
1644     /* Flatten color bitmaps if color was not requested. */
1645     if ( !error                                        &&
1646          !( load_flags & FT_LOAD_COLOR )               &&
1647          !( load_flags & FT_LOAD_BITMAP_METRICS_ONLY ) &&
1648          map->pixel_mode == FT_PIXEL_MODE_BGRA         )
1649     {
1650       FT_Bitmap   new_map;
1651       FT_Library  library = face->root.glyph->library;
1652 
1653 
1654       FT_Bitmap_Init( &new_map );
1655 
1656       /* Convert to 8bit grayscale. */
1657       error = FT_Bitmap_Convert( library, map, &new_map, 1 );
1658       if ( error )
1659         FT_Bitmap_Done( library, &new_map );
1660       else
1661       {
1662         map->pixel_mode = new_map.pixel_mode;
1663         map->pitch      = new_map.pitch;
1664         map->num_grays  = new_map.num_grays;
1665 
1666         ft_glyphslot_set_bitmap( face->root.glyph, new_map.buffer );
1667         face->root.glyph->internal->flags |= FT_GLYPH_OWN_BITMAP;
1668       }
1669     }
1670 
1671     return error;
1672   }
1673 
1674 #else /* !TT_CONFIG_OPTION_EMBEDDED_BITMAPS */
1675 
1676   /* ANSI C doesn't like empty source files */
1677   typedef int  _tt_sbit_dummy;
1678 
1679 #endif /* !TT_CONFIG_OPTION_EMBEDDED_BITMAPS */
1680 
1681 
1682 /* END */