1/***************************************************************************/
2/*                                                                         */
3/*  ttinterp.h                                                             */
4/*                                                                         */
5/*    TrueType bytecode interpreter (specification).                       */
6/*                                                                         */
7/*  Copyright 1996-2017 by                                                 */
8/*  David Turner, Robert Wilhelm, and Werner Lemberg.                      */
9/*                                                                         */
10/*  This file is part of the FreeType project, and may only be used,       */
11/*  modified, and distributed under the terms of the FreeType project      */
12/*  license, LICENSE.TXT.  By continuing to use, modify, or distribute     */
13/*  this file you indicate that you have read the license and              */
14/*  understand and accept it fully.                                        */
15/*                                                                         */
16/***************************************************************************/
17
18
19#ifndef TTINTERP_H_
20#define TTINTERP_H_
21
22#include <ft2build.h>
23#include "ttobjs.h"
24
25
26FT_BEGIN_HEADER
27
28
29  /*************************************************************************/
30  /*                                                                       */
31  /* Rounding mode constants.                                              */
32  /*                                                                       */
33#define TT_Round_Off             5
34#define TT_Round_To_Half_Grid    0
35#define TT_Round_To_Grid         1
36#define TT_Round_To_Double_Grid  2
37#define TT_Round_Up_To_Grid      4
38#define TT_Round_Down_To_Grid    3
39#define TT_Round_Super           6
40#define TT_Round_Super_45        7
41
42
43  /*************************************************************************/
44  /*                                                                       */
45  /* Function types used by the interpreter, depending on various modes    */
46  /* (e.g. the rounding mode, whether to render a vertical or horizontal   */
47  /* line etc).                                                            */
48  /*                                                                       */
49  /*************************************************************************/
50
51  /* Rounding function */
52  typedef FT_F26Dot6
53  (*TT_Round_Func)( TT_ExecContext  exc,
54                    FT_F26Dot6      distance,
55                    FT_F26Dot6      compensation );
56
57  /* Point displacement along the freedom vector routine */
58  typedef void
59  (*TT_Move_Func)( TT_ExecContext  exc,
60                   TT_GlyphZone    zone,
61                   FT_UShort       point,
62                   FT_F26Dot6      distance );
63
64  /* Distance projection along one of the projection vectors */
65  typedef FT_F26Dot6
66  (*TT_Project_Func)( TT_ExecContext  exc,
67                      FT_Pos          dx,
68                      FT_Pos          dy );
69
70  /* getting current ppem.  Take care of non-square pixels if necessary */
71  typedef FT_Long
72  (*TT_Cur_Ppem_Func)( TT_ExecContext  exc );
73
74  /* reading a cvt value.  Take care of non-square pixels if necessary */
75  typedef FT_F26Dot6
76  (*TT_Get_CVT_Func)( TT_ExecContext  exc,
77                      FT_ULong        idx );
78
79  /* setting or moving a cvt value.  Take care of non-square pixels  */
80  /* if necessary                                                    */
81  typedef void
82  (*TT_Set_CVT_Func)( TT_ExecContext  exc,
83                      FT_ULong        idx,
84                      FT_F26Dot6      value );
85
86
87  /*************************************************************************/
88  /*                                                                       */
89  /* This structure defines a call record, used to manage function calls.  */
90  /*                                                                       */
91  typedef struct  TT_CallRec_
92  {
93    FT_Int   Caller_Range;
94    FT_Long  Caller_IP;
95    FT_Long  Cur_Count;
96
97    TT_DefRecord  *Def; /* either FDEF or IDEF */
98
99  } TT_CallRec, *TT_CallStack;
100
101
102#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY
103
104  /*************************************************************************/
105  /*                                                                       */
106  /* These structures define rules used to tweak subpixel hinting for      */
107  /* various fonts.  "", 0, "", NULL value indicates to match any value.   */
108  /*                                                                       */
109
110#define SPH_MAX_NAME_SIZE      32
111#define SPH_MAX_CLASS_MEMBERS  100
112
113  typedef struct  SPH_TweakRule_
114  {
115    const char      family[SPH_MAX_NAME_SIZE];
116    const FT_UInt   ppem;
117    const char      style[SPH_MAX_NAME_SIZE];
118    const FT_ULong  glyph;
119
120  } SPH_TweakRule;
121
122
123  typedef struct  SPH_ScaleRule_
124  {
125    const char      family[SPH_MAX_NAME_SIZE];
126    const FT_UInt   ppem;
127    const char      style[SPH_MAX_NAME_SIZE];
128    const FT_ULong  glyph;
129    const FT_ULong  scale;
130
131  } SPH_ScaleRule;
132
133
134  typedef struct  SPH_Font_Class_
135  {
136    const char  name[SPH_MAX_NAME_SIZE];
137    const char  member[SPH_MAX_CLASS_MEMBERS][SPH_MAX_NAME_SIZE];
138
139  } SPH_Font_Class;
140
141#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */
142
143
144  /*************************************************************************/
145  /*                                                                       */
146  /* The main structure for the interpreter which collects all necessary   */
147  /* variables and states.                                                 */
148  /*                                                                       */
149  typedef struct  TT_ExecContextRec_
150  {
151    TT_Face            face;
152    TT_Size            size;
153    FT_Memory          memory;
154
155    /* instructions state */
156
157    FT_Error           error;      /* last execution error */
158
159    FT_Long            top;        /* top of exec. stack   */
160
161    FT_Long            stackSize;  /* size of exec. stack  */
162    FT_Long*           stack;      /* current exec. stack  */
163
164    FT_Long            args;
165    FT_Long            new_top;    /* new top after exec.  */
166
167    TT_GlyphZoneRec    zp0,        /* zone records */
168                       zp1,
169                       zp2,
170                       pts,
171                       twilight;
172
173    FT_Long            pointSize;  /* in 26.6 format */
174    FT_Size_Metrics    metrics;
175    TT_Size_Metrics    tt_metrics; /* size metrics */
176
177    TT_GraphicsState   GS;         /* current graphics state */
178
179    FT_Int             curRange;  /* current code range number   */
180    FT_Byte*           code;      /* current code range          */
181    FT_Long            IP;        /* current instruction pointer */
182    FT_Long            codeSize;  /* size of current range       */
183
184    FT_Byte            opcode;    /* current opcode              */
185    FT_Int             length;    /* length of current opcode    */
186
187    FT_Bool            step_ins;  /* true if the interpreter must */
188                                  /* increment IP after ins. exec */
189    FT_ULong           cvtSize;
190    FT_Long*           cvt;
191
192    FT_UInt            glyphSize; /* glyph instructions buffer size */
193    FT_Byte*           glyphIns;  /* glyph instructions buffer */
194
195    FT_UInt            numFDefs;  /* number of function defs         */
196    FT_UInt            maxFDefs;  /* maximum number of function defs */
197    TT_DefArray        FDefs;     /* table of FDefs entries          */
198
199    FT_UInt            numIDefs;  /* number of instruction defs */
200    FT_UInt            maxIDefs;  /* maximum number of ins defs */
201    TT_DefArray        IDefs;     /* table of IDefs entries     */
202
203    FT_UInt            maxFunc;   /* maximum function index     */
204    FT_UInt            maxIns;    /* maximum instruction index  */
205
206    FT_Int             callTop,    /* top of call stack during execution */
207                       callSize;   /* size of call stack */
208    TT_CallStack       callStack;  /* call stack */
209
210    FT_UShort          maxPoints;    /* capacity of this context's `pts' */
211    FT_Short           maxContours;  /* record, expressed in points and  */
212                                     /* contours.                        */
213
214    TT_CodeRangeTable  codeRangeTable;  /* table of valid code ranges */
215                                        /* useful for the debugger   */
216
217    FT_UShort          storeSize;  /* size of current storage */
218    FT_Long*           storage;    /* storage area            */
219
220    FT_F26Dot6         period;     /* values used for the */
221    FT_F26Dot6         phase;      /* `SuperRounding'     */
222    FT_F26Dot6         threshold;
223
224    FT_Bool            instruction_trap; /* If `True', the interpreter will */
225                                         /* exit after each instruction     */
226
227    TT_GraphicsState   default_GS;       /* graphics state resulting from   */
228                                         /* the prep program                */
229    FT_Bool            is_composite;     /* true if the glyph is composite  */
230    FT_Bool            pedantic_hinting; /* true if pedantic interpretation */
231
232    /* latest interpreter additions */
233
234    FT_Long            F_dot_P;    /* dot product of freedom and projection */
235                                   /* vectors                               */
236    TT_Round_Func      func_round; /* current rounding function             */
237
238    TT_Project_Func    func_project,   /* current projection function */
239                       func_dualproj,  /* current dual proj. function */
240                       func_freeProj;  /* current freedom proj. func  */
241
242    TT_Move_Func       func_move;      /* current point move function */
243    TT_Move_Func       func_move_orig; /* move original position function */
244
245    TT_Cur_Ppem_Func   func_cur_ppem;  /* get current proj. ppem value  */
246
247    TT_Get_CVT_Func    func_read_cvt;  /* read a cvt entry              */
248    TT_Set_CVT_Func    func_write_cvt; /* write a cvt entry (in pixels) */
249    TT_Set_CVT_Func    func_move_cvt;  /* incr a cvt entry (in pixels)  */
250
251    FT_Bool            grayscale;      /* bi-level hinting and */
252                                       /* grayscale rendering  */
253
254#ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL
255    /*
256     * Modern TrueType fonts are usually rendered through Microsoft's
257     * collection of rendering techniques called ClearType (e.g., subpixel
258     * rendering and subpixel hinting).  When ClearType was introduced, most
259     * fonts were not ready.  Microsoft decided to implement a backwards
260     * compatibility mode that employed several simple to complicated
261     * assumptions and tricks that modified the interpretation of the
262     * bytecode contained in these fonts to make them look ClearType-y
263     * somehow.  Most (web)fonts that were released since then have come to
264     * rely on these hacks to render correctly, even some of Microsoft's
265     * flagship ClearType fonts (Calibri, Cambria, Segoe UI).
266     *
267     * The minimal subpixel hinting code (interpreter version 40) employs a
268     * small list of font-agnostic hacks to bludgeon non-native-ClearType
269     * fonts (except tricky ones[1]) into submission.  It will not try to
270     * toggle hacks for specific fonts for performance and complexity
271     * reasons.  The focus is on modern (web)fonts rather than legacy fonts
272     * that were made for black-and-white rendering.
273     *
274     * Major hacks
275     *
276     * - Any point movement on the x axis is ignored (cf. `Direct_Move' and
277     *   `Direct_Move_X').  This has the smallest code footprint and single
278     *   biggest effect.  The ClearType way to increase resolution is
279     *   supersampling the x axis, the FreeType way is ignoring instructions
280     *   on the x axis, which gives the same result in the majority of
281     *   cases.
282     *
283     * - Points are not moved post-IUP (neither on the x nor on the y axis),
284     *   except the x component of diagonal moves post-IUP (cf.
285     *   `Direct_Move', `Direct_Move_Y', `Move_Zp2_Point').  Post-IUP
286     *   changes are commonly used to `fix' pixel patterns which has little
287     *   use outside monochrome rendering.
288     *
289     * - SHPIX and DELTAP don't execute unless moving a composite on the
290     *   y axis or moving a previously y touched point.  SHPIX additionally
291     *   denies movement on the x axis (cf. `Ins_SHPIX' and `Ins_DELTAP').
292     *   Both instructions are commonly used to `fix' pixel patterns for
293     *   monochrome or Windows's GDI rendering but make little sense for
294     *   FreeType rendering.  Both can distort the outline.  See [2] for
295     *   details.
296     *
297     * - The hdmx table and modifications to phantom points are ignored.
298     *   Bearings and advance widths remain unchanged (except rounding them
299     *   outside the interpreter!), cf. `compute_glyph_metrics' and
300     *   `TT_Hint_Glyph'.  Letting non-native-ClearType fonts modify spacing
301     *   might mess up spacing.
302     *
303     * Minor hacks
304     *
305     * - FLIPRGON, FLIPRGOFF, and FLIPPT don't execute post-IUP.  This
306     *   prevents dents in e.g. Arial-Regular's `D' and `G' glyphs at
307     *   various sizes.
308     *
309     * (Post-IUP is the state after both IUP[x] and IUP[y] have been
310     * executed.)
311     *
312     * The best results are achieved for fonts that were from the outset
313     * designed with ClearType in mind, meaning they leave the x axis mostly
314     * alone and don't mess with the `final' outline to produce more
315     * pleasing pixel patterns.  The harder the designer tried to produce
316     * very specific patterns (`superhinting') for pre-ClearType-displays,
317     * the worse the results.
318     *
319     * Microsoft defines a way to turn off backwards compatibility and
320     * interpret instructions as before (called `native ClearType')[2][3].
321     * The font designer then regains full control and is responsible for
322     * making the font work correctly with ClearType without any
323     * hand-holding by the interpreter or rasterizer[4].  The v40
324     * interpreter assumes backwards compatibility by default, which can be
325     * turned off the same way by executing the following in the control
326     * program (cf. `Ins_INSTCTRL').
327     *
328     *   #PUSH 4,3
329     *   INSTCTRL[]
330     *
331     * [1] Tricky fonts as FreeType defines them rely on the bytecode
332     *     interpreter to display correctly.  Hacks can interfere with them,
333     *     so they get treated like native ClearType fonts (v40 with
334     *     backwards compatibility turned off).  Cf. `TT_RunIns'.
335     *
336     * [2] Proposed by Microsoft's Greg Hitchcock in
337     *     https://www.microsoft.com/typography/cleartype/truetypecleartype.aspx
338     *
339     * [3] Beat Stamm describes it in more detail:
340     *     http://www.beatstamm.com/typography/RTRCh4.htm#Sec12
341     *
342     * [4] The list of `native ClearType' fonts is small at the time of this
343     *     writing; I found the following on a Windows 10 Update 1511
344     *     installation: Constantia, Corbel, Sitka, Malgun Gothic, Microsoft
345     *     JhengHei (Bold and UI Bold), Microsoft YaHei (Bold and UI Bold),
346     *     SimSun, NSimSun, and Yu Gothic.
347     *
348     */
349
350    /* Using v40 implies subpixel hinting.  Used to detect interpreter */
351    /* version switches.  `_lean' to differentiate from the Infinality */
352    /* `subpixel_hinting', which is managed differently.               */
353    FT_Bool            subpixel_hinting_lean;
354
355    /* Long side of a LCD subpixel is vertical (e.g., screen is rotated). */
356    /* `_lean' to differentiate from the Infinality `vertical_lcd', which */
357    /* is managed differently.                                            */
358    FT_Bool            vertical_lcd_lean;
359
360    /* Default to backwards compatibility mode in v40 interpreter.  If  */
361    /* this is false, it implies the interpreter is in v35 or in native */
362    /* ClearType mode.                                                  */
363    FT_Bool            backwards_compatibility;
364
365    /* Useful for detecting and denying post-IUP trickery that is usually */
366    /* used to fix pixel patterns (`superhinting').                       */
367    FT_Bool            iupx_called;
368    FT_Bool            iupy_called;
369
370    /* ClearType hinting and grayscale rendering, as used by Universal */
371    /* Windows Platform apps (Windows 8 and above).  Like the standard */
372    /* colorful ClearType mode, it utilizes a vastly increased virtual */
373    /* resolution on the x axis.  Different from bi-level hinting and  */
374    /* grayscale rendering, the old mode from Win9x days that roughly  */
375    /* adheres to the physical pixel grid on both axes.                */
376    FT_Bool            grayscale_cleartype;
377#endif /* TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL */
378
379#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY
380    TT_Round_Func      func_round_sphn;   /* subpixel rounding function */
381
382    FT_Bool            subpixel_hinting;  /* Using subpixel hinting?       */
383    FT_Bool            ignore_x_mode;     /* Standard rendering mode for   */
384                                          /* subpixel hinting.  On if gray */
385                                          /* or subpixel hinting is on.    */
386
387    /* The following 6 aren't fully implemented but here for MS rasterizer */
388    /* compatibility.                                                      */
389    FT_Bool            compatible_widths;     /* compatible widths?        */
390    FT_Bool            symmetrical_smoothing; /* symmetrical_smoothing?    */
391    FT_Bool            bgr;                   /* bgr instead of rgb?       */
392    FT_Bool            vertical_lcd;          /* long side of LCD subpixel */
393                                              /* rectangles is horizontal  */
394    FT_Bool            subpixel_positioned;   /* subpixel positioned       */
395                                              /* (DirectWrite ClearType)?  */
396    FT_Bool            gray_cleartype;        /* ClearType hinting but     */
397                                              /* grayscale rendering       */
398
399    FT_Int             rasterizer_version;    /* MS rasterizer version     */
400
401    FT_Bool            iup_called;            /* IUP called for glyph?     */
402
403    FT_ULong           sph_tweak_flags;       /* flags to control          */
404                                              /* hint tweaks               */
405
406    FT_ULong           sph_in_func_flags;     /* flags to indicate if in   */
407                                              /* special functions         */
408
409#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */
410
411    /* We maintain two counters (in addition to the instruction counter) */
412    /* that act as loop detectors for LOOPCALL and jump opcodes with     */
413    /* negative arguments.                                               */
414    FT_ULong           loopcall_counter;
415    FT_ULong           loopcall_counter_max;
416    FT_ULong           neg_jump_counter;
417    FT_ULong           neg_jump_counter_max;
418
419  } TT_ExecContextRec;
420
421
422  extern const TT_GraphicsState  tt_default_graphics_state;
423
424
425#ifdef TT_USE_BYTECODE_INTERPRETER
426  FT_LOCAL( void )
427  TT_Goto_CodeRange( TT_ExecContext  exec,
428                     FT_Int          range,
429                     FT_Long         IP );
430
431  FT_LOCAL( void )
432  TT_Set_CodeRange( TT_ExecContext  exec,
433                    FT_Int          range,
434                    void*           base,
435                    FT_Long         length );
436
437  FT_LOCAL( void )
438  TT_Clear_CodeRange( TT_ExecContext  exec,
439                      FT_Int          range );
440
441
442  FT_LOCAL( FT_Error )
443  Update_Max( FT_Memory  memory,
444              FT_ULong*  size,
445              FT_ULong   multiplier,
446              void*      _pbuff,
447              FT_ULong   new_max );
448#endif /* TT_USE_BYTECODE_INTERPRETER */
449
450
451  /*************************************************************************/
452  /*                                                                       */
453  /* <Function>                                                            */
454  /*    TT_New_Context                                                     */
455  /*                                                                       */
456  /* <Description>                                                         */
457  /*    Queries the face context for a given font.  Note that there is     */
458  /*    now a _single_ execution context in the TrueType driver which is   */
459  /*    shared among faces.                                                */
460  /*                                                                       */
461  /* <Input>                                                               */
462  /*    face :: A handle to the source face object.                        */
463  /*                                                                       */
464  /* <Return>                                                              */
465  /*    A handle to the execution context.  Initialized for `face'.        */
466  /*                                                                       */
467  /* <Note>                                                                */
468  /*    Only the glyph loader and debugger should call this function.      */
469  /*    (And right now only the glyph loader uses it.)                     */
470  /*                                                                       */
471  FT_EXPORT( TT_ExecContext )
472  TT_New_Context( TT_Driver  driver );
473
474
475#ifdef TT_USE_BYTECODE_INTERPRETER
476  FT_LOCAL( void )
477  TT_Done_Context( TT_ExecContext  exec );
478
479  FT_LOCAL( FT_Error )
480  TT_Load_Context( TT_ExecContext  exec,
481                   TT_Face         face,
482                   TT_Size         size );
483
484  FT_LOCAL( void )
485  TT_Save_Context( TT_ExecContext  exec,
486                   TT_Size         ins );
487
488  FT_LOCAL( FT_Error )
489  TT_Run_Context( TT_ExecContext  exec );
490#endif /* TT_USE_BYTECODE_INTERPRETER */
491
492
493  /*************************************************************************/
494  /*                                                                       */
495  /* <Function>                                                            */
496  /*    TT_RunIns                                                          */
497  /*                                                                       */
498  /* <Description>                                                         */
499  /*    Executes one or more instruction in the execution context.  This   */
500  /*    is the main function of the TrueType opcode interpreter.           */
501  /*                                                                       */
502  /* <Input>                                                               */
503  /*    exec :: A handle to the target execution context.                  */
504  /*                                                                       */
505  /* <Return>                                                              */
506  /*    FreeType error code.  0 means success.                             */
507  /*                                                                       */
508  /* <Note>                                                                */
509  /*    Only the object manager and debugger should call this function.    */
510  /*                                                                       */
511  /*    This function is publicly exported because it is directly          */
512  /*    invoked by the TrueType debugger.                                  */
513  /*                                                                       */
514  FT_EXPORT( FT_Error )
515  TT_RunIns( TT_ExecContext  exec );
516
517
518FT_END_HEADER
519
520#endif /* TTINTERP_H_ */
521
522
523/* END */
524