[truetype] While tracing opcodes, show code position and stack.

* src/truetype/ttinterp.c: Change all existing TRACE7 calls to
TRACE6.
(opcode_name): Add string lengths.
(TT_RunIns): Implement display of code position and stack.
diff --git a/ChangeLog b/ChangeLog
index d5ea7a0..8d7feee 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,12 @@
+2015-06-01  Werner Lemberg  <wl@gnu.org>
+
+	[truetype] While tracing opcodes, show code position and stack.
+
+	* src/truetype/ttinterp.c: Change all existing TRACE7 calls to
+	TRACE6.
+	(opcode_name): Add string lengths.
+	(TT_RunIns): Implement display of code position and stack.
+
 2015-05-31  Werner Lemberg  <wl@gnu.org>
 
 	[truetype] In GX, make private point numbers work correctly.
diff --git a/src/truetype/ttinterp.c b/src/truetype/ttinterp.c
index 0f9fb0c..06e96c8 100644
--- a/src/truetype/ttinterp.c
+++ b/src/truetype/ttinterp.c
@@ -939,280 +939,284 @@
 
 #ifdef FT_DEBUG_LEVEL_TRACE
 
+  /* the first hex digit gives the length of the opcode name; the space */
+  /* after the digit is here just to increase readability of the source */
+  /* code                                                               */
+
   static
   const char*  const opcode_name[256] =
   {
-    "SVTCA y",
-    "SVTCA x",
-    "SPvTCA y",
-    "SPvTCA x",
-    "SFvTCA y",
-    "SFvTCA x",
-    "SPvTL ||",
-    "SPvTL +",
-    "SFvTL ||",
-    "SFvTL +",
-    "SPvFS",
-    "SFvFS",
-    "GPv",
-    "GFv",
-    "SFvTPv",
-    "ISECT",
+    "7 SVTCA y",
+    "7 SVTCA x",
+    "8 SPvTCA y",
+    "8 SPvTCA x",
+    "8 SFvTCA y",
+    "8 SFvTCA x",
+    "8 SPvTL ||",
+    "7 SPvTL +",
+    "8 SFvTL ||",
+    "7 SFvTL +",
+    "5 SPvFS",
+    "5 SFvFS",
+    "3 GPv",
+    "3 GFv",
+    "6 SFvTPv",
+    "5 ISECT",
 
-    "SRP0",
-    "SRP1",
-    "SRP2",
-    "SZP0",
-    "SZP1",
-    "SZP2",
-    "SZPS",
-    "SLOOP",
-    "RTG",
-    "RTHG",
-    "SMD",
-    "ELSE",
-    "JMPR",
-    "SCvTCi",
-    "SSwCi",
-    "SSW",
+    "4 SRP0",
+    "4 SRP1",
+    "4 SRP2",
+    "4 SZP0",
+    "4 SZP1",
+    "4 SZP2",
+    "4 SZPS",
+    "5 SLOOP",
+    "3 RTG",
+    "4 RTHG",
+    "3 SMD",
+    "4 ELSE",
+    "4 JMPR",
+    "6 SCvTCi",
+    "5 SSwCi",
+    "3 SSW",
 
-    "DUP",
-    "POP",
-    "CLEAR",
-    "SWAP",
-    "DEPTH",
-    "CINDEX",
-    "MINDEX",
-    "AlignPTS",
-    "INS_$28",
-    "UTP",
-    "LOOPCALL",
-    "CALL",
-    "FDEF",
-    "ENDF",
-    "MDAP[0]",
-    "MDAP[1]",
+    "3 DUP",
+    "3 POP",
+    "5 CLEAR",
+    "4 SWAP",
+    "5 DEPTH",
+    "6 CINDEX",
+    "6 MINDEX",
+    "8 AlignPTS",
+    "7 INS_$28",
+    "3 UTP",
+    "8 LOOPCALL",
+    "4 CALL",
+    "4 FDEF",
+    "4 ENDF",
+    "7 MDAP[0]",
+    "7 MDAP[1]",
 
-    "IUP[0]",
-    "IUP[1]",
-    "SHP[0]",
-    "SHP[1]",
-    "SHC[0]",
-    "SHC[1]",
-    "SHZ[0]",
-    "SHZ[1]",
-    "SHPIX",
-    "IP",
-    "MSIRP[0]",
-    "MSIRP[1]",
-    "AlignRP",
-    "RTDG",
-    "MIAP[0]",
-    "MIAP[1]",
+    "6 IUP[0]",
+    "6 IUP[1]",
+    "6 SHP[0]",
+    "6 SHP[1]",
+    "6 SHC[0]",
+    "6 SHC[1]",
+    "6 SHZ[0]",
+    "6 SHZ[1]",
+    "5 SHPIX",
+    "2 IP",
+    "8 MSIRP[0]",
+    "8 MSIRP[1]",
+    "7 AlignRP",
+    "4 RTDG",
+    "7 MIAP[0]",
+    "7 MIAP[1]",
 
-    "NPushB",
-    "NPushW",
-    "WS",
-    "RS",
-    "WCvtP",
-    "RCvt",
-    "GC[0]",
-    "GC[1]",
-    "SCFS",
-    "MD[0]",
-    "MD[1]",
-    "MPPEM",
-    "MPS",
-    "FlipON",
-    "FlipOFF",
-    "DEBUG",
+    "6 NPushB",
+    "6 NPushW",
+    "2 WS",
+    "2 RS",
+    "5 WCvtP",
+    "4 RCvt",
+    "5 GC[0]",
+    "5 GC[1]",
+    "4 SCFS",
+    "5 MD[0]",
+    "5 MD[1]",
+    "5 MPPEM",
+    "3 MPS",
+    "6 FlipON",
+    "7 FlipOFF",
+    "5 DEBUG",
 
-    "LT",
-    "LTEQ",
-    "GT",
-    "GTEQ",
-    "EQ",
-    "NEQ",
-    "ODD",
-    "EVEN",
-    "IF",
-    "EIF",
-    "AND",
-    "OR",
-    "NOT",
-    "DeltaP1",
-    "SDB",
-    "SDS",
+    "2 LT",
+    "4 LTEQ",
+    "2 GT",
+    "4 GTEQ",
+    "2 EQ",
+    "3 NEQ",
+    "3 ODD",
+    "4 EVEN",
+    "2 IF",
+    "3 EIF",
+    "3 AND",
+    "2 OR",
+    "3 NOT",
+    "7 DeltaP1",
+    "3 SDB",
+    "3 SDS",
 
-    "ADD",
-    "SUB",
-    "DIV",
-    "MUL",
-    "ABS",
-    "NEG",
-    "FLOOR",
-    "CEILING",
-    "ROUND[0]",
-    "ROUND[1]",
-    "ROUND[2]",
-    "ROUND[3]",
-    "NROUND[0]",
-    "NROUND[1]",
-    "NROUND[2]",
-    "NROUND[3]",
+    "3 ADD",
+    "3 SUB",
+    "3 DIV",
+    "3 MUL",
+    "3 ABS",
+    "3 NEG",
+    "5 FLOOR",
+    "7 CEILING",
+    "8 ROUND[0]",
+    "8 ROUND[1]",
+    "8 ROUND[2]",
+    "8 ROUND[3]",
+    "9 NROUND[0]",
+    "9 NROUND[1]",
+    "9 NROUND[2]",
+    "9 NROUND[3]",
 
-    "WCvtF",
-    "DeltaP2",
-    "DeltaP3",
-    "DeltaCn[0]",
-    "DeltaCn[1]",
-    "DeltaCn[2]",
-    "SROUND",
-    "S45Round",
-    "JROT",
-    "JROF",
-    "ROFF",
-    "INS_$7B",
-    "RUTG",
-    "RDTG",
-    "SANGW",
-    "AA",
+    "5 WCvtF",
+    "7 DeltaP2",
+    "7 DeltaP3",
+    "A DeltaCn[0]",
+    "A DeltaCn[1]",
+    "A DeltaCn[2]",
+    "6 SROUND",
+    "8 S45Round",
+    "4 JROT",
+    "4 JROF",
+    "4 ROFF",
+    "7 INS_$7B",
+    "4 RUTG",
+    "4 RDTG",
+    "5 SANGW",
+    "2 AA",
 
-    "FlipPT",
-    "FlipRgON",
-    "FlipRgOFF",
-    "INS_$83",
-    "INS_$84",
-    "ScanCTRL",
-    "SDPvTL[0]",
-    "SDPvTL[1]",
-    "GetINFO",
-    "IDEF",
-    "ROLL",
-    "MAX",
-    "MIN",
-    "ScanTYPE",
-    "InstCTRL",
-    "INS_$8F",
+    "6 FlipPT",
+    "8 FlipRgON",
+    "9 FlipRgOFF",
+    "7 INS_$83",
+    "7 INS_$84",
+    "8 ScanCTRL",
+    "9 SDPvTL[0]",
+    "9 SDPvTL[1]",
+    "7 GetINFO",
+    "4 IDEF",
+    "4 ROLL",
+    "3 MAX",
+    "3 MIN",
+    "8 ScanTYPE",
+    "8 InstCTRL",
+    "7 INS_$8F",
 
-    "INS_$90",
-    "INS_$91",
-    "INS_$92",
-    "INS_$93",
-    "INS_$94",
-    "INS_$95",
-    "INS_$96",
-    "INS_$97",
-    "INS_$98",
-    "INS_$99",
-    "INS_$9A",
-    "INS_$9B",
-    "INS_$9C",
-    "INS_$9D",
-    "INS_$9E",
-    "INS_$9F",
+    "7 INS_$90",
+    "7 INS_$91",
+    "7 INS_$92",
+    "7 INS_$93",
+    "7 INS_$94",
+    "7 INS_$95",
+    "7 INS_$96",
+    "7 INS_$97",
+    "7 INS_$98",
+    "7 INS_$99",
+    "7 INS_$9A",
+    "7 INS_$9B",
+    "7 INS_$9C",
+    "7 INS_$9D",
+    "7 INS_$9E",
+    "7 INS_$9F",
 
-    "INS_$A0",
-    "INS_$A1",
-    "INS_$A2",
-    "INS_$A3",
-    "INS_$A4",
-    "INS_$A5",
-    "INS_$A6",
-    "INS_$A7",
-    "INS_$A8",
-    "INS_$A9",
-    "INS_$AA",
-    "INS_$AB",
-    "INS_$AC",
-    "INS_$AD",
-    "INS_$AE",
-    "INS_$AF",
+    "7 INS_$A0",
+    "7 INS_$A1",
+    "7 INS_$A2",
+    "7 INS_$A3",
+    "7 INS_$A4",
+    "7 INS_$A5",
+    "7 INS_$A6",
+    "7 INS_$A7",
+    "7 INS_$A8",
+    "7 INS_$A9",
+    "7 INS_$AA",
+    "7 INS_$AB",
+    "7 INS_$AC",
+    "7 INS_$AD",
+    "7 INS_$AE",
+    "7 INS_$AF",
 
-    "PushB[0]",
-    "PushB[1]",
-    "PushB[2]",
-    "PushB[3]",
-    "PushB[4]",
-    "PushB[5]",
-    "PushB[6]",
-    "PushB[7]",
-    "PushW[0]",
-    "PushW[1]",
-    "PushW[2]",
-    "PushW[3]",
-    "PushW[4]",
-    "PushW[5]",
-    "PushW[6]",
-    "PushW[7]",
+    "8 PushB[0]",
+    "8 PushB[1]",
+    "8 PushB[2]",
+    "8 PushB[3]",
+    "8 PushB[4]",
+    "8 PushB[5]",
+    "8 PushB[6]",
+    "8 PushB[7]",
+    "8 PushW[0]",
+    "8 PushW[1]",
+    "8 PushW[2]",
+    "8 PushW[3]",
+    "8 PushW[4]",
+    "8 PushW[5]",
+    "8 PushW[6]",
+    "8 PushW[7]",
 
-    "MDRP[00]",
-    "MDRP[01]",
-    "MDRP[02]",
-    "MDRP[03]",
-    "MDRP[04]",
-    "MDRP[05]",
-    "MDRP[06]",
-    "MDRP[07]",
-    "MDRP[08]",
-    "MDRP[09]",
-    "MDRP[10]",
-    "MDRP[11]",
-    "MDRP[12]",
-    "MDRP[13]",
-    "MDRP[14]",
-    "MDRP[15]",
+    "8 MDRP[00]",
+    "8 MDRP[01]",
+    "8 MDRP[02]",
+    "8 MDRP[03]",
+    "8 MDRP[04]",
+    "8 MDRP[05]",
+    "8 MDRP[06]",
+    "8 MDRP[07]",
+    "8 MDRP[08]",
+    "8 MDRP[09]",
+    "8 MDRP[10]",
+    "8 MDRP[11]",
+    "8 MDRP[12]",
+    "8 MDRP[13]",
+    "8 MDRP[14]",
+    "8 MDRP[15]",
 
-    "MDRP[16]",
-    "MDRP[17]",
-    "MDRP[18]",
-    "MDRP[19]",
-    "MDRP[20]",
-    "MDRP[21]",
-    "MDRP[22]",
-    "MDRP[23]",
-    "MDRP[24]",
-    "MDRP[25]",
-    "MDRP[26]",
-    "MDRP[27]",
-    "MDRP[28]",
-    "MDRP[29]",
-    "MDRP[30]",
-    "MDRP[31]",
+    "8 MDRP[16]",
+    "8 MDRP[17]",
+    "8 MDRP[18]",
+    "8 MDRP[19]",
+    "8 MDRP[20]",
+    "8 MDRP[21]",
+    "8 MDRP[22]",
+    "8 MDRP[23]",
+    "8 MDRP[24]",
+    "8 MDRP[25]",
+    "8 MDRP[26]",
+    "8 MDRP[27]",
+    "8 MDRP[28]",
+    "8 MDRP[29]",
+    "8 MDRP[30]",
+    "8 MDRP[31]",
 
-    "MIRP[00]",
-    "MIRP[01]",
-    "MIRP[02]",
-    "MIRP[03]",
-    "MIRP[04]",
-    "MIRP[05]",
-    "MIRP[06]",
-    "MIRP[07]",
-    "MIRP[08]",
-    "MIRP[09]",
-    "MIRP[10]",
-    "MIRP[11]",
-    "MIRP[12]",
-    "MIRP[13]",
-    "MIRP[14]",
-    "MIRP[15]",
+    "8 MIRP[00]",
+    "8 MIRP[01]",
+    "8 MIRP[02]",
+    "8 MIRP[03]",
+    "8 MIRP[04]",
+    "8 MIRP[05]",
+    "8 MIRP[06]",
+    "8 MIRP[07]",
+    "8 MIRP[08]",
+    "8 MIRP[09]",
+    "8 MIRP[10]",
+    "8 MIRP[11]",
+    "8 MIRP[12]",
+    "8 MIRP[13]",
+    "8 MIRP[14]",
+    "8 MIRP[15]",
 
-    "MIRP[16]",
-    "MIRP[17]",
-    "MIRP[18]",
-    "MIRP[19]",
-    "MIRP[20]",
-    "MIRP[21]",
-    "MIRP[22]",
-    "MIRP[23]",
-    "MIRP[24]",
-    "MIRP[25]",
-    "MIRP[26]",
-    "MIRP[27]",
-    "MIRP[28]",
-    "MIRP[29]",
-    "MIRP[30]",
-    "MIRP[31]"
+    "8 MIRP[16]",
+    "8 MIRP[17]",
+    "8 MIRP[18]",
+    "8 MIRP[19]",
+    "8 MIRP[20]",
+    "8 MIRP[21]",
+    "8 MIRP[22]",
+    "8 MIRP[23]",
+    "8 MIRP[24]",
+    "8 MIRP[25]",
+    "8 MIRP[26]",
+    "8 MIRP[27]",
+    "8 MIRP[28]",
+    "8 MIRP[29]",
+    "8 MIRP[30]",
+    "8 MIRP[31]"
   };
 
 #endif /* FT_DEBUG_LEVEL_TRACE */
@@ -3684,7 +3688,7 @@
 
             if ( opcode_pointer[i] == opcode_size[i] )
             {
-              FT_TRACE7(( "sph: Function %d, opcode ptrn: %d, %s %s\n",
+              FT_TRACE6(( "sph: Function %d, opcode ptrn: %d, %s %s\n",
                           i, n,
                           exc->face->root.family_name,
                           exc->face->root.style_name ));
@@ -7320,7 +7324,7 @@
         /* if in ClearType backwards compatibility mode,        */
         /* we sometimes change the TrueType version dynamically */
         K = exc->rasterizer_version;
-        FT_TRACE7(( "Setting rasterizer version %d\n",
+        FT_TRACE6(( "Setting rasterizer version %d\n",
                     exc->rasterizer_version ));
       }
       else
@@ -7556,9 +7560,26 @@
     {
       exc->opcode = exc->code[exc->IP];
 
-      FT_TRACE7(( "  " ));
-      FT_TRACE7(( opcode_name[exc->opcode] ));
-      FT_TRACE7(( "\n" ));
+#ifdef FT_DEBUG_LEVEL_TRACE
+      {
+        FT_Long  cnt = FT_MIN( 8, exc->top );
+        FT_Long  n;
+
+
+        /* if tracing level is 7, show current code position */
+        /* and the first few stack elements also             */
+        FT_TRACE6(( "  " ));
+        FT_TRACE7(( "%06d ", exc->IP ));
+        FT_TRACE6(( opcode_name[exc->opcode] + 2 ));
+        FT_TRACE7(( "%*s", *opcode_name[exc->opcode] == 'A'
+                              ? 2
+                              : 12 - ( *opcode_name[exc->opcode] - '0' ),
+                              "#" ));
+        for ( n = 0; n < cnt; n++ )
+          FT_TRACE7(( " %d", exc->stack[exc->top - n] ));
+        FT_TRACE6(( "\n" ));
+      }
+#endif /* FT_DEBUG_LEVEL_TRACE */
 
       if ( ( exc->length = opcode_length[exc->opcode] ) < 0 )
       {
@@ -7617,7 +7638,7 @@
 
             if ( opcode_pointer[i] == opcode_size[i] )
             {
-              FT_TRACE7(( "sph: opcode ptrn: %d, %s %s\n",
+              FT_TRACE6(( "sph: opcode ptrn: %d, %s %s\n",
                           i,
                           exc->face->root.family_name,
                           exc->face->root.style_name ));