/***************************************************************************/
/*                                                                         */
/*  gxvm.c                                                                 */
/*                                                                         */
/*    AAT/TrueTypeGX glyph substitution automaton (body).                  */
/*                                                                         */
/*  Copyright 2003 by                                                      */
/*  Masatake YAMATO and Redhat K.K.                                        */
/*                                                                         */
/*  This file may only be used,                                            */
/*  modified, and distributed under the terms of the FreeType project      */
/*  license, LICENSE.TXT.  By continuing to use, modify, or distribute     */
/*  this file you indicate that you have read the license and              */
/*  understand and accept it fully.                                        */
/*                                                                         */
/***************************************************************************/

/***************************************************************************/
/* Development of the code in this file is support of                      */
/* Information-technology Promotion Agency, Japan.                         */
/***************************************************************************/

#include <ft2build.h>
#include FT_INTERNAL_DEBUG_H
#include FT_LAYOUT_H
#include FT_LIST_H
#include "gxvm.h"
#include "gxutils.h"
#include "gxerrors.h"

#undef  FT_COMPONENT
#define FT_COMPONENT  trace_gxvm


  /*************************************************************************/
  /*************************************************************************/
  /*************************************************************************/
  /****                                                                 ****/
  /****                                                                 ****/
  /****                        Ligature Stack                           ****/
  /****                                                                 ****/
  /****                                                                 ****/
  /*************************************************************************/
  /*************************************************************************/
  /*************************************************************************/

#define LIGATURE_STACK_DEPTH 16
typedef struct LigatureStackRec_
{  
  FT_Char depth;
  FT_Char top;
  FT_Char ligatured_top;
  FT_ULong indexes[LIGATURE_STACK_DEPTH];
  FT_ULong ligatured_indexes[LIGATURE_STACK_DEPTH];
} LigatureStackRec, *LigatureStack;

static void ligstack_init(LigatureStack stack);
static void ligstack_push( LigatureStack stack, 
			   FT_ULong index );
static FT_ULong ligstack_pop( LigatureStack stack );
static void     ligstack_unify(LigatureStack stack);
static void     ligstack_ligatured_init(LigatureStack stack);
static void     ligstack_ligatured_push(LigatureStack stack,
				    FT_ULong index );

static FT_Bool  ligstack_ligatured_empty(LigatureStack stack);
static FT_ULong ligstack_ligatured_pop(LigatureStack stack);



static void
ligstack_init(LigatureStack stack)
{
  FT_Int i;
  stack->depth = LIGATURE_STACK_DEPTH;
  stack->top = -1;
  for ( i = 0; i < stack->depth; i++ )
    stack->indexes[i]   = 0;
  ligstack_ligatured_init( stack );
}

static void
ligstack_push( LigatureStack stack, FT_ULong index )
{
  stack->top++;
  if ( stack->top >= stack->depth )
    stack->top = 0;
  stack->indexes[stack->top] = index;
}

static FT_ULong
ligstack_pop( LigatureStack stack )
{
  FT_ULong index;
  
  index = stack->indexes[stack->top];
  stack->top--;
  if ( stack->top < 0 )
    stack->top= stack->depth - 1;
  return index;
}


static void
ligstack_unify(LigatureStack stack)
{
  FT_ULong index;
  while ( !ligstack_ligatured_empty ( stack ) )
    {
      index = ligstack_ligatured_pop( stack );
      ligstack_push( stack, index );
  }
}

static void
ligstack_ligatured_init(LigatureStack stack)
{
  stack->ligatured_top = -1;
}

static void
ligstack_ligatured_push(LigatureStack stack,
			FT_ULong index )
{
  stack->ligatured_top++;
  if ( stack->ligatured_top >= stack->depth )
    stack->ligatured_top 			 = 0;
  stack->ligatured_indexes[stack->ligatured_top] = index;
}

static FT_Bool
ligstack_ligatured_empty(LigatureStack stack)
{
  return (stack->ligatured_top >= 0)? 0: 1;
}

static FT_ULong
ligstack_ligatured_pop(LigatureStack stack)
{
  FT_ULong index;
  /* ??? */
  index = stack->ligatured_indexes[stack->ligatured_top];
  if ( stack->ligatured_top > -1 )
    stack->ligatured_top--;
  return index;
}


  
  /*************************************************************************/
  /*************************************************************************/
  /*************************************************************************/
  /****                                                                 ****/
  /****                                                                 ****/
  /****                          Glyphs List                            ****/
  /****                                                                 ****/
  /****                                                                 ****/
  /*************************************************************************/
  /*************************************************************************/
  /*************************************************************************/

#define INSERTION_GLYPHS_MAX 31
  typedef struct InsertionGlyphsRec_
  {
    FTL_GlyphRec glyphs[INSERTION_GLYPHS_MAX];
    FT_UShort length;
  } InsertionGlyphsRec, *InsertionGlyphs;

  typedef struct GlyphNodeRec_
  {
    FT_ListNodeRec root;
    FTL_GlyphRec   glyph;
  } GlyphNodeRec, *GlyphNode;


  typedef struct GlyphsListRec_
  {
    FT_ListRec       root;
    GlyphNode        current;
    GlyphNode        mark;
    FT_Memory        memory;
  } GlyphsListRec, *GlyphsList;

  typedef FT_Error 
  (* GList_InsertFunc)( GlyphsList glist, 
			InsertionGlyphs insertion,
			FT_Bool before );

  static void insertion_glyphs_init ( InsertionGlyphs glyphs );
  static void insertion_glyphs_push ( InsertionGlyphs glyphs, FT_UShort gid );
  static FT_Error insertion_glyphs_store ( InsertionGlyphs glyphs,
					   FT_Memory memory,
					   FT_List list );

  static void
  insertion_glyphs_init ( InsertionGlyphs glyphs )
  {
    glyphs->length = 0;
  }
  static void
  insertion_glyphs_push ( InsertionGlyphs glyphs, FT_UShort gid )
  {
    if (!( glyphs->length < INSERTION_GLYPHS_MAX ))
      glyphs->length = 0;
    glyphs->glyphs[glyphs->length].gid = gid;
  }

  static FT_Error
  insertion_glyphs_store ( InsertionGlyphs glyphs, 
			   FT_Memory memory,
			   FT_List list )
  {
    FT_UShort i;
    FT_Error error = FT_Err_Ok;
    GlyphNode gnode;
    
    for ( i = 0; i < glyphs->length; i++ )
      {
	if ( FT_NEW( gnode ) )
	  goto Failure;
	gnode->glyph = glyphs->glyphs[i];
	FT_List_Add( list, (FT_ListNode)gnode );
      }
    return error;
  Failure:
    FT_List_Finalize( list, NULL, memory, NULL );
    return error;
  }

  static FT_Error glist_init    ( FT_Memory memory, 
				  GlyphsList glist,
				  FTL_GlyphArray garray );
  static FT_Error glist_store   ( GlyphsList glist, 
				  FTL_GlyphArray garray );
  static void glist_finalize    ( GlyphsList glist );

/*
 * GList_InsertFunc
 */
  static FT_Error glist_insert_current      ( GlyphsList glist, 
					      InsertionGlyphs insertion,
					      FT_Bool before );
  static FT_Error glist_insert_mark         ( GlyphsList glist, 
					      InsertionGlyphs insertion,
					      FT_Bool before );

  static void      glist_set_mark    ( GlyphsList glist );
  static FTL_Glyph glist_get_next    ( GlyphsList glist );
  static FTL_Glyph glist_get_current ( GlyphsList glist );

/* glist function group local;
   - glist_insert_before_*
   - glist_insert_after_*
   - glist_insert */
  static FT_Error glist_insert_before_current( GlyphsList glist, InsertionGlyphs insertion );
  static FT_Error glist_insert_after_current ( GlyphsList glist, InsertionGlyphs insertion );
  static FT_Error glist_insert_before_mark   ( GlyphsList glist, InsertionGlyphs insertion );
  static FT_Error glist_insert_after_mark    ( GlyphsList glist, InsertionGlyphs insertion );
  static FT_Error glist_insert               ( GlyphsList glist, 
					       FT_ListNode before, 
					       FT_ListNode after, 
					       InsertionGlyphs insertion );

  static FT_Error
  glist_init    ( FT_Memory memory, GlyphsList glist, FTL_GlyphArray garray )
  {
    FT_Error error;
    FT_ULong i;
    GlyphNode glyph_node;
    
    ((FT_List)glist)->head = NULL;
    ((FT_List)glist)->tail = NULL;
    glist->mark 	   = NULL;
    glist->memory 	   = memory;

    for ( i = 0; i < garray->length; i++ )
      {
	if ( FT_NEW(glyph_node) )
	  goto Failure;
	glyph_node->glyph = garray->glyphs[i];
	FT_List_Add((FT_List)glist, (FT_ListNode)glyph_node);
      }
    glist->current = (GlyphNode)((FT_List)glist)->head;
    
    return FT_Err_Ok;
  Failure:
    FT_List_Finalize( (FT_List)glist, NULL, memory, NULL );
    return error;
  }

  static FT_Error
  glist_store   ( GlyphsList glist, FTL_GlyphArray garray )
  {
    FT_Error error;
    FT_ULong length = 0, i;
    FT_ListNode tmp;
    
    tmp = glist->root.head;
    while ( tmp )
      {
	length++;
	tmp = tmp->next;
      }

    if (( error = FTL_Set_Glyphs_Array_Length( garray, length ) ))
      return error;
    
    tmp = glist->root.head;
    for ( i = 0; i < length; i++ )
      {
	garray->glyphs[i] = ((GlyphNode)tmp)->glyph;
	tmp 		  = tmp->next;
      }
    return error;
  }

  static void
  glist_finalize( GlyphsList glist )
  {
    FT_Memory memory = glist->memory;
    FT_List_Finalize( (FT_List)glist, NULL, memory, NULL );
  }

  static FT_Error
  glist_insert_current      ( GlyphsList glist, 
			      InsertionGlyphs insertion,
			      FT_Bool before )
  {
    return ( before
	     ? glist_insert_before_current( glist, insertion )
	     : glist_insert_after_current( glist, insertion ));
  }

  static FT_Error
  glist_insert_mark         ( GlyphsList glist, 
			      InsertionGlyphs insertion,
			      FT_Bool before )
  {
    return ( before 
	     ? glist_insert_before_mark( glist, insertion )
	     : glist_insert_after_mark( glist, insertion ));
  }

  static FT_Error
  glist_insert_before_current( GlyphsList glist, InsertionGlyphs insertion )
  {
    FT_ListNode before, after;
    
    after = (FT_ListNode)glist->current;
    FT_ASSERT( after );
    before = after->prev;
    return glist_insert(glist, before, after, insertion);
  }

  static FT_Error
  glist_insert_after_current ( GlyphsList glist, InsertionGlyphs insertion )
  {
    FT_ListNode before, after;
    
    before = (FT_ListNode)glist->current; 
    FT_ASSERT( before );
    after = before->next;
    return glist_insert(glist, before, after, insertion);
  }

  static FT_Error
  glist_insert_before_mark   ( GlyphsList glist, InsertionGlyphs insertion )
  {
    FT_ListNode before, after;
    
    after = (FT_ListNode)glist->mark;
    FT_ASSERT( after );
    before = after->prev;
    return glist_insert(glist, before, after, insertion);
  }

  static FT_Error
  glist_insert_after_mark    ( GlyphsList glist, InsertionGlyphs insertion )
  {
    FT_ListNode before, after;
    
    before = (FT_ListNode)glist->mark; 
    FT_ASSERT( before );
    after = before->next;
    return glist_insert(glist, before, after, insertion);
  }

  static FT_Error
  glist_insert               ( GlyphsList glist, 
			       FT_ListNode before, 
			       FT_ListNode after, 
			       InsertionGlyphs insertion )
  {
    FT_Error error;
    FT_ListRec insertion_list = {NULL, NULL};
    FT_Memory memory 	= glist->memory;
    FT_ListNode head, tail;
    
    if (( error = insertion_glyphs_store( insertion,
					  memory,
					  &insertion_list ) ))
      return error;
    head = insertion_list.head;
    tail = insertion_list.tail;

    if ( (!head) && (!tail) )
      return FT_Err_Ok;
    
    FT_ASSERT( head );
    FT_ASSERT( tail );

    
    if ( before )
      {
	before->next = head;
	head->prev   = before;
      }
    else
      {
	glist->root.head = head;
	head->prev 	 = NULL;
      }

    if ( after )
      {
	after->prev = tail;
	tail->next  = after;
      }
    else
      {
	glist->root.tail = tail;
	tail->next 	 = NULL;
      }
    return FT_Err_Ok;
  }

  static void
  glist_set_mark        ( GlyphsList glist )
  {
    glist->mark = glist->current;
  }

  static FTL_Glyph
  glist_get_next    ( GlyphsList glist )
  {
    if ( !glist->current )
      return NULL;
    
    glist->current = ( GlyphNode )glist->current->root.next;
    return glist_get_current ( glist );
  }

  static FTL_Glyph
  glist_get_current ( GlyphsList glist )
  {
    return ( glist->current )? &(glist->current->glyph): NULL;
  }
  

  /*************************************************************************/
  /*************************************************************************/
  /*************************************************************************/
  /****                                                                 ****/
  /****                                                                 ****/
  /****                        Glyph Metamorphosis                      ****/
  /****                                                                 ****/
  /****                                                                 ****/
  /*************************************************************************/
  /*************************************************************************/
  /*************************************************************************/


/*************************************************************************
 * Noncontextual
 *************************************************************************/ 
FT_LOCAL_DEF( FT_Error )
gx_noncontextual_subst( GX_MetamorphosisNoncontextualBody body,
			FTL_GlyphArray garray )
{
  FT_ULong i;
  GX_LookupTable lookup_table = &body->lookup_table;
  GX_LookupResultRec result;
  
  FT_TRACE2(("Enter noncontextual\n"));
  for ( i = 0; i < garray->length; i++ )
    {
      if ( garray->glyphs[i].gid == GX_DELETED_GLYPH_INDEX )
	continue ;
      result = gx_LookupTable_lookup ( lookup_table, garray->glyphs[i].gid );
      if ( result.value == NULL )
	continue;
      
      if ( result.firstGlyph == GX_LOOKUP_RESULT_NO_FIRST_GLYPH )
	{
	  FT_TRACE3(("	Substitution[%lu] %u to %u\n",
		     i, garray->glyphs[i].gid, result.value->raw.u));
	  garray->glyphs[i].gid = result.value->raw.u;
	}
      else
	{
	  FT_TRACE3(( "	Substitution[%d] %u to %u\n", 
		     i, garray->glyphs[i].gid,
		      result.value->extra.word[garray->glyphs[i].gid - result.firstGlyph] ));
	  garray->glyphs[i].gid = result.value->extra.word[garray->glyphs[i].gid - result.firstGlyph];
	}
    }
  FT_TRACE2(("Leave noncontextual\n"));
  return FT_Err_Ok;
}

	
/*************************************************************************
 * Contextual
 *************************************************************************/   
static FT_UShort contextual_lookup_glyph( GX_MetamorphosisContextualBody body,
					  FT_Short index, /* Was:FT_UShort, see gxtype.h */
					  FT_UShort gid );

FT_LOCAL_DEF( FT_Error )
gx_contextual_subst( GX_MetamorphosisContextualBody body,
		     GXL_Initial_State initial_state,
		     FTL_GlyphArray garray )
{
  FT_ULong glength  = garray->length;
  FTL_Glyph glyphs = garray->glyphs;
  FT_UShort current_state;

  FT_ULong current_glyph, mark_glyph;
  FT_Byte class_code, final_class;
  GX_EntrySubtable entry_subtable;
  
  FT_Short markOffset, currentOffset; /* Was:FT_UShort, see gxtype.h */
  FT_UShort tmp;
  
  FT_TRACE2(("Enter contextual\n"));

  current_glyph = 0;
  mark_glyph 	= 0;
  current_state = body->state_table.header.stateArray + (FT_Byte)initial_state;
  final_class = ( initial_state == GXL_START_OF_TEXT_STATE )
    ? GX_CLASS_END_OF_TEXT: GX_CLASS_END_OF_LINE;
  
  while ( current_glyph <= glength )
    {
      FT_TRACE3(("  glyph id: %u, glyph position: %lu/%lu\n", 
		 current_glyph == glength? 0xFFFF: glyphs[current_glyph].gid,
		 current_glyph, glength ));

      /* glyph -> class */
      class_code = ( current_glyph == glength )
	? final_class: gx_StateTable_get_class ( &body->state_table, 
						 glyphs[current_glyph].gid );
      FT_TRACE3(("  class code: %u current state: %u\n", class_code, current_state ));
      
      /* class -> entry */
      entry_subtable = gx_StateTable_get_entry_subtable ( &body->state_table,
							  current_state, 
							  class_code );

      /* action for entry */
      currentOffset = entry_subtable->glyphOffsets.contextual->currentOffset;
      markOffset    = entry_subtable->glyphOffsets.contextual->markOffset;
      if ( currentOffset )
	{
	  FT_TRACE3((" currentOffset is given: %d\n", currentOffset)); /* Was:FT_UShort, see gxtype.h. */
	  tmp = glyphs[current_glyph].gid;
	  glyphs[current_glyph].gid = contextual_lookup_glyph(body, currentOffset, tmp);
	  FT_TRACE3(("	Substitution[current %lu] %u to %u\n",
		     current_glyph, tmp, glyphs[current_glyph].gid ));
	}
      if ( markOffset )
	{
	  FT_TRACE3((" markOffset is given: %d\n", markOffset)); /* Was:FT_UShort, see gxtype.h. */
	  tmp = glyphs[mark_glyph].gid;
	  glyphs[mark_glyph].gid = contextual_lookup_glyph(body, markOffset, tmp);
	  FT_TRACE3(("	Substitution[current %lu] %u to %u\n",
		     mark_glyph, tmp, glyphs[current_glyph].gid ));
	}
      
      /* set mark */
      if ( entry_subtable->flags & GX_MORT_CONTEXTUAL_FLAGS_SET_MARK )
	{
	  mark_glyph = current_glyph;
	  FT_TRACE3(("	%ld is marked.\n", mark_glyph ));
	}

      /* advance */
      if ( !(entry_subtable->flags & GX_MORT_CONTEXTUAL_FLAGS_DONT_ADVANCE ) )
	{
	  FT_TRACE3(("	index++.\n"));
	  current_glyph++;
	}

      /* new state */
      current_state = entry_subtable->newState;
    }
  FT_TRACE2(("Leave contextual\n"));
  return FT_Err_Ok;
}

static FT_UShort
contextual_lookup_glyph( GX_MetamorphosisContextualBody body,
			 FT_Short offset, /* Was:FT_UShort, see gxtype.h */
			 FT_UShort gid )
{
  GX_MetamorphosisContextualSubstitutionTable substitution_table = &body->substitutionTable;
  FT_ULong index;
  
  FT_TRACE2(("offset: %u substitution_table->offset %u\n",
	     offset, substitution_table->offset ));
  index = (2 * offset - substitution_table->offset)/2 + gid;
  FT_TRACE2(("index: %lu < substitution_table->nGlyphIndexes: %lu\n",
	     index, substitution_table->nGlyphIndexes));
  FT_ASSERT( index < substitution_table->nGlyphIndexes );
  return substitution_table->glyph_indexes[index];
}

/*************************************************************************
 * Ligature
 *************************************************************************/ 
static FT_ULong * ligature_get_action( GX_MetamorphosisLigatureBody body,
				       FT_UShort action_offset );
static FT_UShort ligature_get_component( GX_MetamorphosisLigatureBody body,
					 FT_Long component_offset,
					 FT_UShort gid );

static FT_UShort ligature_get_ligature ( GX_MetamorphosisLigatureBody body,
					 FT_ULong action,
					 FT_Long  accumulator );
					 
FT_LOCAL_DEF( FT_Error )
gx_ligature_subst( GX_MetamorphosisLigatureBody body,
		   GXL_Initial_State initial_state,
		   FTL_GlyphArray garray )
{
  FT_ULong glength  = garray->length;
  FTL_Glyph glyphs = garray->glyphs;
  FT_UShort current_state;

  FT_ULong current_glyph, component_glyph;
  FT_Byte class_code, final_class;
  GX_EntrySubtable entry_subtable;

  LigatureStackRec ligstack;
  FT_UShort action_offset;
  FT_ULong *action;

  FT_UShort component;
  FT_Long component_offset;
  FT_Long component_accumulator;
  FT_UShort tmp;
  
  FT_TRACE2(("Enter ligature\n"));
  
  current_glyph = 0;
  current_state = body->state_table.header.stateArray + (FT_Byte)initial_state;
  final_class = ( initial_state == GXL_START_OF_TEXT_STATE )
    ? GX_CLASS_END_OF_TEXT: GX_CLASS_END_OF_LINE;
  ligstack_init(&ligstack);
  while ( current_glyph <= glength )
    {
      FT_TRACE3(("  glyph id: %u, glyph position: %lu/%lu\n", 
		 current_glyph == glength? 0xFFFF: glyphs[current_glyph].gid,
		 current_glyph, glength ));

      /* glyph -> class */
      class_code = ( current_glyph == glength )
	? final_class: gx_StateTable_get_class ( &body->state_table, 
						 glyphs[current_glyph].gid );
      FT_TRACE3(("  class code: %u current state: %u\n", class_code, current_state ));
      
      /* class -> entry */
      entry_subtable = gx_StateTable_get_entry_subtable ( &body->state_table,
							  current_state, 
							  class_code );

      /* action for entry */
      if ( entry_subtable->flags & GX_MORT_LIGATURE_FLAGS_SET_COMPONENT )
	{
	  FT_TRACE3(("	Push[current_glyph %lu] %lu to the stack\n",
		     current_glyph, glyphs[current_glyph] ));
	  ligstack_push(&ligstack, current_glyph);
	}
      
      /* action */
      action_offset = entry_subtable->flags & GX_MORT_LIGATURE_FLAGS_OFFSET;
      if ( action_offset ) 
	{
	  action = ligature_get_action( body, action_offset ) - 1;
	  component_accumulator = 0;
	  ligstack_ligatured_init( &ligstack );

	  do {
	    action++;
	    component_glyph  = ligstack_pop( &ligstack );
	    component_offset = (*action) & GX_MORT_LIGATURE_ACTION_OFFSET;
	    if ( component_offset ) 
	      {
		component = ligature_get_component( body, 
						    component_offset,
						    glyphs[component_glyph].gid );
		component_accumulator += component;
		tmp = ligature_get_ligature( body, 
					     *action,
					     component_accumulator );
		FT_TRACE3(("	Substitution[component %lu] %u to %u\n",
			   component_glyph, glyphs[component_glyph].gid, tmp ));
		glyphs[component_glyph].gid = tmp; 
		if (*action & ( GX_MORT_LIGATURE_ACTION_LAST | 
				GX_MORT_LIGATURE_ACTION_STORE ))
		    {
		      ligstack_ligatured_push( &ligstack, component_glyph );
		      component_accumulator = 0;
		    }
	      }
	  } while (! ((*action) & GX_MORT_LIGATURE_ACTION_LAST));
	  ligstack_unify ( &ligstack );
	}
      
      /* advance */
      if ( !(entry_subtable->flags & GX_MORT_LIGATURE_FLAGS_DONT_ADVANCE ) )
	{
	  FT_TRACE3(("	index++.\n"));
	  current_glyph++;
	}
      
      /* new state */
      current_state = entry_subtable->newState;
    }
  FT_TRACE2(("Leave ligature\n"));
  return FT_Err_Ok;
}

static FT_ULong *
ligature_get_action( GX_MetamorphosisLigatureBody body, 
		     FT_UShort action_offset )
{
  FT_UShort action_index;
  GX_MetamorphosisLigatureActionTable action_table = &body->ligActionTable;
  FT_ASSERT( ((action_offset - action_table->offset)%4 == 0) );
  action_index = (action_offset - action_table->offset)/4;
  return &(action_table->body[action_index]);
}

static FT_UShort
ligature_get_component( GX_MetamorphosisLigatureBody body,
			FT_Long component_offset,
			FT_UShort gid )
{
  FT_Long component_index;
  GX_MetamorphosisComponentTable component_table = &body->componentTable;
  
  component_offset = gx_sign_extend ( component_offset,
				      GX_MORT_LIGATURE_ACTION_OFFSET );
  component_index = (2 * component_offset - component_table->offset)/2 + gid;
  FT_ASSERT ( component_index < component_table->nComponent );
  return component_table->body[component_index];
}

static FT_UShort
ligature_get_ligature ( GX_MetamorphosisLigatureBody body,
			FT_ULong action,
			FT_Long  accumulator )
{
  FT_Long ligature_index;
  GX_MetamorphosisLigatureTable ligature_table = &body->ligatureTable;
  
  ligature_index = (accumulator - ligature_table->offset)/2;
  FT_ASSERT ( ligature_index < ligature_table->nLigature );

  if (action & ( GX_MORT_LIGATURE_ACTION_LAST
		 | GX_MORT_LIGATURE_ACTION_STORE ))
    return ligature_table->body[ligature_index];
  else
    return GX_DELETED_GLYPH_INDEX;
}

/*************************************************************************
 * Insertion
 *************************************************************************/ 

static FT_Error
insertion_insert ( GX_MetamorphosisInsertionList insertion,
		   FT_UShort  flags,
		   FT_UShort  count_mask,
		   FT_UShort  pos_mask,
		   GList_InsertFunc insert,
		   GlyphsList glist );

/* TODO: insert Tracer */
FT_LOCAL_DEF( FT_Error )
gx_insertion_subst( GX_MetamorphosisInsertionBody body,
		    GXL_Initial_State initial_state,
		    FTL_GlyphArray garray )
{
  FT_Error error;
  FT_Memory memory = garray->memory;
  
  GlyphsListRec glist;
  FTL_Glyph current_glyph;
  FT_UShort current_state;
  
  FT_Byte class_code, final_class;
  GX_EntrySubtable entry_subtable;
  
  GX_MetamorphosisInsertionList current_insertion;
  GX_MetamorphosisInsertionList marked_insertion;
  
  FT_TRACE2(("Enter insertion\n"));
  
  if (( error = glist_init(memory, &glist, garray) ))
    return error;

  current_state = body->state_table.header.stateArray + (FT_Byte)initial_state;
  final_class = ( initial_state == GXL_START_OF_TEXT_STATE )
    ? GX_CLASS_END_OF_TEXT: GX_CLASS_END_OF_LINE;
  
  do {
    current_glyph = glist_get_current(&glist);
    
    /* glyph -> class */
    class_code  = ( current_glyph == NULL) 
      ? final_class: gx_StateTable_get_class( &body->state_table,
					      current_glyph->gid );
    FT_TRACE3(("  class code: %u current state: %u\n", class_code, current_state ));
    
    /* class -> entry */
    entry_subtable = gx_StateTable_get_entry_subtable( &body->state_table,
						       current_state,
						       class_code );
    /* action for entry */
    current_insertion = &entry_subtable->glyphOffsets.insertion->currentInsertList;
    marked_insertion  = &entry_subtable->glyphOffsets.insertion->markedInsertList;
    if ( current_insertion->offset )
      {
	if (( error = insertion_insert ( current_insertion,
					 entry_subtable->flags,
					 GX_MORT_INSERTION_FLAGS_CURRENT_INSERT_COUNT,
					 GX_MORT_INSERTION_FLAGS_CURRENT_INSERT_BEFORE,
					 glist_insert_current,
					 &glist ) ))
	  goto Failure;
      }
    
    if ( marked_insertion->offset )
      {
	if (( error = insertion_insert ( marked_insertion,
					 entry_subtable->flags,
					 GX_MORT_INSERTION_FLAGS_MARKED_INSERT_COUNT,
					 GX_MORT_INSERTION_FLAGS_MARKED_INSERT_BEFORE,
					 glist_insert_mark,
					 &glist ) ))
	  goto Failure;
      }
    
    /* set mark */
    if ( entry_subtable->flags & GX_MORT_INSERTION_FLAGS_SET_MARK )
      glist_set_mark( &glist );
    
    /* advance */
    if (!( entry_subtable->flags & GX_MORT_INSERTION_FLAGS_DONT_ADVANCE ))
      (void)glist_get_next( &glist );

    /* new state */
    current_state = entry_subtable->newState;
  } while ( current_glyph );
  
  FT_TRACE2(("Leave insertion\n"));
  if (( error = glist_store ( &glist, garray ) ))
    goto Failure;
  glist_finalize( &glist );
  return error;
 Failure:
  glist_finalize( &glist );
  return error;
}

static FT_Error
insertion_insert ( GX_MetamorphosisInsertionList insertion,
		   FT_UShort  flags,
		   FT_UShort  count_mask,
		   FT_UShort  pos_mask,
		   GList_InsertFunc insert,
		   GlyphsList glist )
{
  FT_Int count, i;
  FT_Bool before;
  InsertionGlyphsRec glyphs;
  
  
  count = gx_mask_zero_shift(flags, count_mask);
  before = (flags & pos_mask) ? 1: 0;
  
  insertion_glyphs_init ( &glyphs );
  for ( i = 0; i < count; i++ )
    insertion_glyphs_push( &glyphs, insertion->glyphcodes[i] );
  /* TODO: kashida like or split vowels */
  return insert( glist, &glyphs, before );
}

/*************************************************************************
 * Rearrangement
 *************************************************************************/ 
static void rearrangement_rearrange( GX_MetamorphosisRearrangementVerb verb,
				     FT_ULong first_glyph,
				     FT_ULong last_glyph,
				     FTL_GlyphArray garray );
FT_LOCAL( FT_Error )
gx_rearrangement_subst ( GX_MetamorphosisRearrangementBody body,
			 GXL_Initial_State initial_state,
			 FTL_GlyphArray garray )
{
  FT_ULong glength  = garray->length;
  FTL_Glyph glyphs = garray->glyphs;
  FT_UShort current_state;
  
  FT_ULong current_glyph, first_glyph, last_glyph;
  FT_Byte class_code, final_class;
  GX_EntrySubtable entry_subtable;

  GX_MetamorphosisRearrangementVerb verb;
  
  FT_TRACE2(("Enter rearrangement\n"));
  current_glyph = 0;
  first_glyph 	= 0;
  last_glyph 	= 0;
  current_state = body->state_table.header.stateArray + (FT_Byte)initial_state;
  final_class = ( initial_state == GXL_START_OF_TEXT_STATE )
    ? GX_CLASS_END_OF_TEXT: GX_CLASS_END_OF_LINE;

  while ( current_glyph <= glength )
    {
      FT_TRACE3(("  glyph id: %u, glyph position: %lu/%lu\n", 
		 current_glyph == glength? 0xFFFF: glyphs[current_glyph].gid,
		 current_glyph, glength ));

      /* glyph -> class */
      class_code = ( current_glyph == glength )
	? final_class: gx_StateTable_get_class ( &body->state_table, 
						 glyphs[current_glyph].gid ); 
      FT_TRACE3(("  class code: %u current state: %u\n", class_code, current_state ));

      /* class -> entry */
      entry_subtable = gx_StateTable_get_entry_subtable ( &body->state_table,
							  current_state, 
							  class_code );
      /* action for entry */
      if ( entry_subtable->flags & GX_MORT_REARRANGEMENT_FLAGS_MARK_FIRST )
	{
	  FT_TRACE3(( "	set %lu as first\n", current_glyph ));
	  first_glyph = current_glyph;
	}
      if ( entry_subtable->flags & GX_MORT_REARRANGEMENT_FLAGS_MARK_LAST )
	{
	  FT_TRACE3(( "	set %lu as last\n", current_glyph ));
	  last_glyph = current_glyph;
	}
      
      /* rearrange */
      verb = entry_subtable->flags & GX_MORT_REARRANGEMENT_FLAGS_VERB;
      FT_TRACE3(("	verb %d\n", verb));
      rearrangement_rearrange( verb, first_glyph, last_glyph, garray );
      
      /* advance */
      if ( !(entry_subtable->flags & GX_MORT_REARRANGEMENT_FLAGS_DONT_ADVANCE) )
	{
	  FT_TRACE3(("  index++.\n"));
	  current_glyph++;
	}

      /* new state */
      current_state = entry_subtable->newState; 
    }
  FT_TRACE2(("Leave rearrangement\n"));
  return FT_Err_Ok;
}

static void
rearrangement_rearrange( GX_MetamorphosisRearrangementVerb verb,
			 FT_ULong first_glyph,
			 FT_ULong last_glyph,
			 FTL_GlyphArray garray )
{
  FTL_Glyph glyphs = garray->glyphs;
  FT_ULong glength  = garray->length;
  
  FTL_GlyphRec A, B, C, D;
  FT_ULong x;


  /* Treat VERB_NO_CHANGE as a special case; return
     before "first_glyph <= last_glyph" assertion. */  
  if ( verb == GX_MORT_REARRANGEMENT_VERB_NO_CHANGE )
    return ;
  
  FT_ASSERT ( first_glyph <= last_glyph );
  FT_ASSERT ( first_glyph < glength );
  FT_ASSERT ( last_glyph  < glength );
  
  switch ( verb )
    {
    case GX_MORT_REARRANGEMENT_VERB_Ax2xA:
      A = glyphs[first_glyph];
      for ( x = first_glyph + 1; x <= last_glyph; x++ )
	glyphs[x - 1] 	 = glyphs[x];
      glyphs[last_glyph] = A;
      break;
      
    case GX_MORT_REARRANGEMENT_VERB_xD2Dx:
      D = glyphs[last_glyph];
      for ( x = last_glyph - 1; x >= first_glyph; x-- )
	glyphs[x + 1] = glyphs[x];
      glyphs[first_glyph] = D;
      break;
      
    case GX_MORT_REARRANGEMENT_VERB_AxD2DxA:
      A 		  = glyphs[first_glyph];
      D 		  = glyphs[last_glyph];
      glyphs[first_glyph] = D;
      glyphs[last_glyph]  = A;
      break;

    case GX_MORT_REARRANGEMENT_VERB_ABx2xAB:
      FT_ASSERT( first_glyph + 1 < glength );
      FT_ASSERT( first_glyph + 2 <= last_glyph );
      FT_ASSERT( last_glyph - 1  >= 0 );
      
      A = glyphs[first_glyph];
      B = glyphs[first_glyph + 1];
      for ( x = first_glyph + 2; x <= last_glyph; x++ )
	glyphs[x - 2] 	     = glyphs[x];
      glyphs[last_glyph - 1] = A;
      glyphs[last_glyph]     = B;
      break;
      
    case GX_MORT_REARRANGEMENT_VERB_ABx2xBA:
      FT_ASSERT( first_glyph + 1 < glength );
      FT_ASSERT( first_glyph + 2 <= last_glyph );
      FT_ASSERT( last_glyph - 1  >= 0 );
      
      A = glyphs[first_glyph];
      B = glyphs[first_glyph + 1];
      for ( x = first_glyph + 2; x <= last_glyph; x++ )
	glyphs[x - 2] = glyphs[x];
      
      glyphs[last_glyph - 1] = B;
      glyphs[last_glyph]     = A;
      break;

    case GX_MORT_REARRANGEMENT_VERB_xCD2CDx:
      FT_ASSERT( last_glyph - 1 >= 0 );
      FT_ASSERT( first_glyph 	<= last_glyph - 2 );
      FT_ASSERT( first_glyph + 1 < glength );
      C = glyphs[last_glyph - 1];
      D = glyphs[last_glyph];
      for ( x = last_glyph - 2; x >= first_glyph; x-- )
	glyphs[x + 2] 	  =  glyphs[x];

      glyphs[first_glyph]     = C;
      glyphs[first_glyph + 1] = D;
      break;
      
    case GX_MORT_REARRANGEMENT_VERB_xCD2DCx:
      FT_ASSERT( last_glyph - 1 >= 0 );
      FT_ASSERT( first_glyph 	<= last_glyph - 2 );
      FT_ASSERT( first_glyph + 1 < glength );
      C = glyphs[last_glyph - 1];
      D = glyphs[last_glyph];
      for ( x = last_glyph - 2; x >= first_glyph; x-- )
	glyphs[x + 2] 	  =  glyphs[x];

      glyphs[first_glyph]     = D;
      glyphs[first_glyph + 1] = C;
      break;

    case GX_MORT_REARRANGEMENT_VERB_AxCD2CDxA:
      FT_ASSERT( last_glyph - 2 >= 0 );
      FT_ASSERT( first_glyph + 1 < glength );
      A = glyphs[first_glyph];
      C = glyphs[last_glyph - 1];
      D = glyphs[last_glyph];
      for ( x = last_glyph - 2; x > first_glyph; x-- )
	glyphs[x + 1] = glyphs[x];
      glyphs[first_glyph] = C;
      glyphs[first_glyph + 1] = D;
      glyphs[last_glyph]      = A;
      break;
      
    case GX_MORT_REARRANGEMENT_VERB_AxCD2DCxA:
      FT_ASSERT( last_glyph - 2 >= 0 );
      FT_ASSERT( first_glyph + 1 < glength );
      A = glyphs[first_glyph];
      C = glyphs[last_glyph - 1];
      D = glyphs[last_glyph];
      
      for ( x = last_glyph - 2; x > first_glyph; x-- )
	glyphs[x + 1] = glyphs[x];
      
      glyphs[first_glyph]     = D;
      glyphs[first_glyph + 1] = C;
      glyphs[last_glyph]      = A;
      break;
      
    case GX_MORT_REARRANGEMENT_VERB_ABxD2DxAB:
      FT_ASSERT ( first_glyph + 2 < glength );
      FT_ASSERT ( last_glyph - 1 >= 0 );
      A = glyphs[first_glyph];
      B = glyphs[first_glyph + 1];
      D	= glyphs[last_glyph];
      for ( x = first_glyph + 2; x < last_glyph; x++ )
	glyphs[x - 2] 	     = glyphs[x];
      glyphs[first_glyph]    = D;
      glyphs[last_glyph - 1] = A;
      glyphs[last_glyph]     = B;
      break;
      
    case GX_MORT_REARRANGEMENT_VERB_ABxD2DxBA:
      FT_ASSERT ( first_glyph + 2 < glength );
      FT_ASSERT ( last_glyph - 1 >= 0 );
      A = glyphs[first_glyph];
      B = glyphs[first_glyph + 1];
      D	= glyphs[last_glyph];
      for ( x = first_glyph + 2; x < last_glyph; x++ )
	glyphs[x - 2] 	     = glyphs[x];
      glyphs[first_glyph]    = D;
      glyphs[last_glyph - 1] = B;
      glyphs[last_glyph]     = A;
      break;

    case GX_MORT_REARRANGEMENT_VERB_ABxCD2CDxAB:
      FT_ASSERT( first_glyph + 1 < glength );
      FT_ASSERT( last_glyph - 1 >= 0 );
      A = glyphs[first_glyph];
      B = glyphs[first_glyph + 1];
      C = glyphs[last_glyph - 1];
      D = glyphs[last_glyph];
      glyphs[first_glyph]     = C;
      glyphs[first_glyph + 1] = D;
      glyphs[last_glyph - 1]  = A;
      glyphs[last_glyph]      = B;
      break;

    case GX_MORT_REARRANGEMENT_VERB_ABxCD2CDxBA:
      FT_ASSERT( first_glyph + 1 < glength );
      FT_ASSERT( last_glyph - 1 >= 0 );
      A = glyphs[first_glyph];
      B = glyphs[first_glyph + 1];
      C = glyphs[last_glyph - 1];
      D = glyphs[last_glyph];
      glyphs[first_glyph]     = C;
      glyphs[first_glyph + 1] = D;
      glyphs[last_glyph - 1]  = B;
      glyphs[last_glyph]      = A;
      break;

    case GX_MORT_REARRANGEMENT_VERB_ABxCD2DCxAB:
      FT_ASSERT( first_glyph + 1 < glength );
      FT_ASSERT( last_glyph - 1 >= 0 );
      A = glyphs[first_glyph];
      B = glyphs[first_glyph + 1];
      C = glyphs[last_glyph - 1];
      D = glyphs[last_glyph];
      glyphs[first_glyph]     = D;
      glyphs[first_glyph + 1] = C;
      glyphs[last_glyph - 1]  = A;
      glyphs[last_glyph]      = B;
      break;
    case GX_MORT_REARRANGEMENT_VERB_ABxCD2DCxBA:
      FT_ASSERT( first_glyph + 1 < glength );
      FT_ASSERT( last_glyph - 1 >= 0 );
      A = glyphs[first_glyph];
      B = glyphs[first_glyph + 1];
      C = glyphs[last_glyph - 1];
      D = glyphs[last_glyph];
      glyphs[first_glyph]     = D;
      glyphs[first_glyph + 1] = C;
      glyphs[last_glyph - 1]  = B;
      glyphs[last_glyph]      = A;
      break;
    default:
      break;			/* TODO: Broken verb */
    }
}



  /*************************************************************************/
  /*************************************************************************/
  /*************************************************************************/
  /****                                                                 ****/
  /****                                                                 ****/
  /****                   Extended Glyph Metamorphosis                  ****/
  /****                                                                 ****/
  /****                                                                 ****/
  /*************************************************************************/
  /*************************************************************************/
  /*************************************************************************/

/*************************************************************************
 * Contextual
 *************************************************************************/ 

static FT_UShort xcontextual_lookup_glyph( GX_XMetamorphosisContextualBody body,
					   FT_UShort lookup_table_index,
					   FT_UShort glyph );

FT_LOCAL_DEF( FT_Error )
gx_xcontextual_subst( GX_XMetamorphosisContextualBody body,
		      GXL_Initial_State initial_state,
		      FTL_GlyphArray garray )
{
  
  FT_ULong glength  = garray->length;
  FTL_Glyph glyphs = garray->glyphs;
  FT_UShort current_state;
  
  FT_ULong current_glyph, mark_glyph;
  FT_UShort class_code, final_class;
  GX_EntrySubtable entry_subtable;

  FT_UShort markIndex, currentIndex;
  FT_UShort tmp;
  
  FT_TRACE2(("Enter xcontextual\n"));
  
  current_glyph = 0;
  mark_glyph 	= 0;
  current_state = 0;
  final_class = ( initial_state == GXL_START_OF_TEXT_STATE )
    ? GX_CLASS_END_OF_TEXT: GX_CLASS_END_OF_LINE;
  
  while  ( current_glyph <= glength )
    {
      FT_TRACE3(("  glyph id: %u, glyph position: %lu/%lu\n", 
		 current_glyph == glength? 0xFFFF: glyphs[current_glyph].gid,
		 current_glyph, glength ));

      
      /* glyph -> class */
      class_code = ( current_glyph == glength )
	? final_class: gx_XStateTable_get_class ( &body->state_table,
						  glyphs[current_glyph].gid );
      FT_TRACE3(("  class code: %u current state: %u\n", class_code, current_state ));
      
      /* class -> entry */
      entry_subtable = gx_XStateTable_get_entry_subtable ( &body->state_table,
							   current_state, 
							   class_code );
      
      currentIndex = entry_subtable->glyphOffsets.contextual->currentOffset;
      markIndex    = entry_subtable->glyphOffsets.contextual->markOffset;
      if ( currentIndex != GX_MORX_NO_SUBSTITUTION )
	{
	  tmp = glyphs[current_glyph].gid;
	  glyphs[current_glyph].gid = xcontextual_lookup_glyph( body,
								currentIndex,
							        glyphs[current_glyph].gid );
	  FT_TRACE3(("	Substitution[current %lu] %u to %u\n",
		     current_glyph, tmp, glyphs[current_glyph].gid ));
	}
      if ( markIndex != GX_MORX_NO_SUBSTITUTION )
	{
	  tmp = glyphs[mark_glyph].gid;
	  glyphs[mark_glyph].gid = xcontextual_lookup_glyph( body,
							     markIndex,
							     glyphs[mark_glyph].gid );
	  FT_TRACE3(("	Substitution[mark %lu] %u to %u\n",
		     mark_glyph, tmp, glyphs[mark_glyph].gid ));
	}

      if ( entry_subtable->flags & GX_MORX_CONTEXTUAL_FLAGS_SET_MARK )
	{
	  mark_glyph = current_glyph;
	  FT_TRACE3(("	%ld is marked.\n", mark_glyph ));
	}

      /* advance */
      if  ( !(entry_subtable->flags & GX_MORX_CONTEXTUAL_FLAGS_DONT_ADVANCE ) )
	{
	  FT_TRACE3(("	index++.\n"));
	  current_glyph++;
	}
      current_state = entry_subtable->newState;
    }
  FT_TRACE2(("Leave contextual\n"));
  return FT_Err_Ok;
}

static FT_UShort
xcontextual_lookup_glyph( GX_XMetamorphosisContextualBody body,
			  FT_UShort lookup_table_index,
			  FT_UShort glyph )
{
  GX_LookupTable * lookupTables;
  GX_LookupResultRec result;
  FT_ASSERT( lookup_table_index < body->substitutionTable.nTables );
  
  lookupTables = body->substitutionTable.lookupTables;
  result       = gx_LookupTable_lookup( lookupTables[lookup_table_index], glyph );
  if ( result.value == NULL )
    return glyph;		/* ??? */
  else if ( result.firstGlyph == GX_LOOKUP_RESULT_NO_FIRST_GLYPH )
    return result.value->raw.u;
  else
    return result.value->extra.word[glyph - result.firstGlyph];
}

/*************************************************************************
 * Ligature
 *************************************************************************/ 

static FT_ULong * xligature_get_action( GX_XMetamorphosisLigatureBody body, 
					FT_UShort action_index );
static FT_UShort  xligature_get_component( GX_XMetamorphosisLigatureBody body,
					   FT_Long component_index_base,
					   FT_UShort gid );
static FT_UShort xligature_get_ligature ( GX_XMetamorphosisLigatureBody body,
					  FT_ULong action,
					  FT_Long  ligature_index );

FT_LOCAL_DEF( FT_Error )
gx_xligature_subst( GX_XMetamorphosisLigatureBody body,
		    GXL_Initial_State initial_state,
		    FTL_GlyphArray garray )
{
  FT_ULong glength  = garray->length;
  FTL_Glyph glyphs = garray->glyphs;
  FT_UShort current_state;

  FT_ULong current_glyph, component_glyph;
  FT_UShort class_code, final_class;
  GX_EntrySubtable entry_subtable;

  LigatureStackRec ligstack;
  FT_UShort action_index;
  FT_ULong *action;

  FT_UShort component;
  FT_Long component_index_base;
  FT_Long component_accumulator;
  FT_UShort tmp;
  
  FT_TRACE2(("Enter xligature\n"));
  
  current_glyph = 0;
  current_state = 0;
  final_class = ( initial_state == GXL_START_OF_TEXT_STATE )
    ? GX_CLASS_END_OF_TEXT: GX_CLASS_END_OF_LINE;

  ligstack_init( &ligstack );
  while ( current_glyph <= glength )
    {
      FT_TRACE3(("  glyph id: %u, glyph position: %lu/%lu\n", 
		 current_glyph == glength? 0xFFFF: glyphs[current_glyph].gid,
		 current_glyph, glength ));

      /* glyph -> class */
      class_code = ( current_glyph == glength )
	? final_class: gx_XStateTable_get_class ( &body->state_table, 
						  glyphs[current_glyph].gid );
      FT_TRACE3(("  class code: %u current state: %u\n", class_code, current_state ));
      
      /* class -> entry */
      entry_subtable = gx_XStateTable_get_entry_subtable ( &body->state_table,
							   current_state, 
							   class_code );
      
      /* action for entry */
      if ( entry_subtable->flags & GX_MORX_LIGATURE_FLAGS_SET_COMPONENT )
	{
	  FT_TRACE3(("	Push[current_glyph %lu] %lu to the stack\n",
		     current_glyph, glyphs[current_glyph] ));
	  ligstack_push(&ligstack, current_glyph);
	}

      if ( entry_subtable->flags & GX_MORX_LIGATURE_FLAGS_PERFORM_ACTION )
	{
	  action_index = entry_subtable->glyphOffsets.ligActionIndex;
	  action = xligature_get_action( body,  action_index ) - 1;
	  component_accumulator = 0;
	  ligstack_ligatured_init( &ligstack );

	  do {
	    action++;
	    component_glyph  = ligstack_pop( &ligstack );
	    FT_TRACE3(("	Pop[component_glyph %lu] %u from the stack\n",
		       component_glyph, glyphs[component_glyph].gid ));
	    FT_TRACE3(("	Action[last %d, store %d]\n",
		       (*action & ( GX_MORX_LIGATURE_ACTION_LAST ))?1:0,
		       (*action & ( GX_MORX_LIGATURE_ACTION_STORE ))?1:0 ));
	    component_index_base = (*action) & GX_MORX_LIGATURE_ACTION_OFFSET;
	    component = xligature_get_component( body, 
						 component_index_base,
						 glyphs[component_glyph].gid );
	    component_accumulator += component;
	    tmp = xligature_get_ligature( body, 
					  *action,
					  component_accumulator );
	    FT_TRACE3(("	Substitution[component %lu] %u to %u\n",
		       component_glyph, glyphs[component_glyph].gid, tmp ));
	    glyphs[component_glyph].gid = tmp; 
	    if (*action & ( GX_MORX_LIGATURE_ACTION_LAST |
			    GX_MORX_LIGATURE_ACTION_STORE ))
	      {
		ligstack_ligatured_push( &ligstack, component_glyph );
		component_accumulator = 0;
	      }
	  } while (! ((*action) & GX_MORX_LIGATURE_ACTION_LAST));
	  ligstack_unify ( &ligstack );
	}
      
      /* advance */
      if ( !(entry_subtable->flags & GX_MORX_LIGATURE_FLAGS_DONT_ADVANCE ) )
	{
	  FT_TRACE3(("	index++.\n"));
	  current_glyph++;
	}
      
      /* new state */
      current_state = entry_subtable->newState;
    }
  FT_TRACE2(("Leave xligature\n"));
  return FT_Err_Ok;
}

static FT_ULong *
xligature_get_action( GX_XMetamorphosisLigatureBody body, 
		       FT_UShort action_index )
{
  GX_XMetamorphosisLigatureActionTable action_table = &body->ligActionTable;
  FT_ASSERT( (action_index < action_table->nActions ) );
  return &(action_table->body[action_index]);
}

static FT_UShort
xligature_get_component( GX_XMetamorphosisLigatureBody body,
			 FT_Long component_index_base,
			 FT_UShort gid )
{
  FT_Long component_index;
  GX_XMetamorphosisComponentTable component_table = &body->componentTable;
  component_index = gx_sign_extend ( component_index_base,
				     GX_MORX_LIGATURE_ACTION_OFFSET )
    + gid;
  FT_ASSERT ( component_index < component_table->nComponent );
  return component_table->body[component_index];
}

static FT_UShort
xligature_get_ligature ( GX_XMetamorphosisLigatureBody body,
			 FT_ULong action,
			 FT_Long  ligature_index )
{
  GX_XMetamorphosisLigatureTable ligature_table = &body->ligatureTable;

  FT_ASSERT ( ligature_index < ligature_table->nLigature );

  if (action & ( GX_MORT_LIGATURE_ACTION_LAST
		 | GX_MORT_LIGATURE_ACTION_STORE ))
    return ligature_table->body[ligature_index];
  else
    return GX_DELETED_GLYPH_INDEX;
}

/*************************************************************************
 * Insertion
 *************************************************************************/ 
#define xinsertion_insert insertion_insert

FT_LOCAL_DEF( FT_Error )
gx_xinsertion_subst( GX_XMetamorphosisInsertionBody body,
		     GXL_Initial_State initial_state,
		     FTL_GlyphArray garray )
{
  FT_Error error;
  FT_Memory memory = garray->memory;
  
  GlyphsListRec glist;
  FTL_Glyph current_glyph;
  FT_UShort current_state;  

  FT_Byte class_code, final_class;
  GX_EntrySubtable entry_subtable;  

  GX_MetamorphosisInsertionList current_insertion;
  GX_MetamorphosisInsertionList marked_insertion;

  
  FT_TRACE2(("Enter xinsertion\n"));

  if (( error = glist_init(memory, &glist, garray) ))
    return error;
  
  current_state = 0;
  final_class = ( initial_state == GXL_START_OF_TEXT_STATE )
    ? GX_CLASS_END_OF_TEXT: GX_CLASS_END_OF_LINE;

  do {
    current_glyph = glist_get_current(&glist);
    
    /* glyph -> class */
    class_code  = ( current_glyph == NULL) 
      ? final_class: gx_XStateTable_get_class( &body->state_table,
					       current_glyph->gid );
    FT_TRACE3(("  class code: %u current state: %u\n", class_code, current_state ));
    
    /* class -> entry */
    entry_subtable = gx_XStateTable_get_entry_subtable ( &body->state_table,
							 current_state, 
							 class_code );

    /* action for entry */
    current_insertion = &entry_subtable->glyphOffsets.insertion->currentInsertList;
    marked_insertion  = &entry_subtable->glyphOffsets.insertion->markedInsertList;
    if ( current_insertion->offset != GX_MORX_NO_INSERTION )
      {
	if (( error = xinsertion_insert( current_insertion,
					 entry_subtable->flags,
					 GX_MORX_INSERTION_FLAGS_CURRENT_INSERT_COUNT,
					 GX_MORX_INSERTION_FLAGS_CURRENT_INSERT_BEFORE,
					 glist_insert_current,
					 &glist )))
	  goto Failure;
      }
    if ( marked_insertion->offset != GX_MORX_NO_INSERTION )
      {
	if ((error = xinsertion_insert( marked_insertion,
					entry_subtable->flags,
					GX_MORX_INSERTION_FLAGS_MARKED_INSERT_COUNT,
					GX_MORX_INSERTION_FLAGS_MARKED_INSERT_BEFORE,
					glist_insert_mark,
					&glist )))
	  goto Failure;
      }
    /* set mark */
    if ( entry_subtable->flags & GX_MORX_INSERTION_FLAGS_SET_MARK )
      glist_set_mark( &glist );
    
    /* advance */
    if ( !(entry_subtable->flags & GX_MORX_INSERTION_FLAGS_DONT_ADVANCE) )
      (void)glist_get_next( &glist );

    /* new state */
    current_state = entry_subtable->newState;
  } while ( current_glyph );
  
  FT_TRACE2(("Leave xinsertion\n"));
  if (( error = glist_store ( &glist, garray ) ))
    goto Failure;
  glist_finalize( &glist );
  return error;
 Failure:
  glist_finalize( &glist );
  return error;
}

/*************************************************************************
 * Rearrangement
 *************************************************************************/ 
#define xrearrangement_rearrange rearrangement_rearrange

FT_LOCAL( FT_Error )
gx_xrearrangement_subst ( GX_XMetamorphosisRearrangementBody body,
			  GXL_Initial_State initial_state,
			  FTL_GlyphArray garray )

{
  FT_ULong glength  = garray->length;
  FTL_Glyph glyphs = garray->glyphs;
  FT_UShort current_state;
  
  FT_ULong current_glyph, first_glyph, last_glyph;
  FT_UShort class_code, final_class;
  GX_EntrySubtable entry_subtable;

  GX_XMetamorphosisRearrangementVerb verb;
  
  FT_TRACE2(("Enter xrearrangement\n"));

  current_glyph = 0;
  first_glyph 	= 0;
  last_glyph 	= 0;
  current_state = 0;
  final_class = ( initial_state == GXL_START_OF_TEXT_STATE )
    ? GX_CLASS_END_OF_TEXT: GX_CLASS_END_OF_LINE;

  while ( current_glyph <= glength )
    {
      FT_TRACE3(("  glyph id: %u, glyph position: %lu/%lu\n", 
		 current_glyph == glength? 0xFFFF: glyphs[current_glyph].gid,
		 current_glyph, glength ));

      /* glyph -> class */
      class_code = ( current_glyph == glength )
	? final_class: gx_XStateTable_get_class ( &body->state_table, 
						  glyphs[current_glyph].gid ); 
      FT_TRACE3(("  class code: %u current state: %u\n", class_code, current_state ));
      
      /* class -> entry */
      entry_subtable = gx_XStateTable_get_entry_subtable ( &body->state_table,
							   current_state, 
							   class_code );
      /* action for entry */
      if ( entry_subtable->flags & GX_MORX_REARRANGEMENT_FLAGS_MARK_FIRST )
	{
	  FT_TRACE3(( "	set %lu as first\n", current_glyph ));
	  first_glyph = current_glyph;
	}
      if ( entry_subtable->flags & GX_MORX_REARRANGEMENT_FLAGS_MARK_LAST )
	{
	  FT_TRACE3(( "	set %lu as last\n", current_glyph ));
	  last_glyph = current_glyph;
	}
      
      /* rearrange */
      verb = entry_subtable->flags & GX_MORX_REARRANGEMENT_FLAGS_VERB;
      FT_TRACE3(("	verb %d\n", verb));
      xrearrangement_rearrange( verb, first_glyph, last_glyph, garray );
      
      /* advance */
      if ( !(entry_subtable->flags & GX_MORX_REARRANGEMENT_FLAGS_DONT_ADVANCE) ) 
	{
	  FT_TRACE3(("  index++.\n"));
	  current_glyph++;
	}

      /* new state */
      current_state = entry_subtable->newState;      
    }
  FT_TRACE2(("Leave xrearrangement\n"));
  return FT_Err_Ok;
}


  /*************************************************************************/
  /*************************************************************************/
  /*************************************************************************/
  /****                                                                 ****/
  /****                                                                 ****/
  /****                        Kerning Stack                            ****/
  /****                                                                 ****/
  /****                                                                 ****/
  /*************************************************************************/
  /*************************************************************************/
  /*************************************************************************/

#define KERNING_STACK_DEPTH 8
typedef LigatureStackRec KerningStackRec;
typedef LigatureStack    KerningStack;
static void kernstack_init( KerningStack stack );
#define kernstack_push ligstack_push
#define kernstack_pop  ligstack_pop
static void
kernstack_init( KerningStack stack )
{
  FT_Int i;
  stack->depth = KERNING_STACK_DEPTH;
  stack->top = -1;
  for ( i = 0; i < stack->depth; i++ )
    stack->indexes[i]   = 0;
}

  /*************************************************************************/
  /*************************************************************************/
  /*************************************************************************/
  /****                                                                 ****/
  /****                                                                 ****/
  /****                        Contextual Kerning                       ****/
  /****                                                                 ****/
  /****                                                                 ****/
  /*************************************************************************/
  /*************************************************************************/
  /*************************************************************************/

FT_LOCAL_DEF( FT_Error )
gx_contextual_kerning_calc ( GX_KerningSubtableFormat1Body kern_fmt1,
			     FTL_GlyphArray garray,
			     FTL_Direction dir,
			     FT_Bool cross_stream,
			     GXL_Initial_State initial_state,
			     FT_Vector * kerning )
{
  FT_ULong  glength = garray->length;
  FTL_Glyph glyphs  = garray->glyphs;
  FT_UShort current_state;
  
  FT_ULong current_glyph, applied_glyph;
  FT_Byte class_code, final_class;
  GX_EntrySubtable entry_subtable;

  KerningStackRec kernstack;
  FT_UShort value_offset;
  FT_UShort value_index;
  FT_FWord raw_value, value;
  FT_Pos total_cross_stream = 0;
  FT_Pos * target;

  
  current_glyph = 0;
  current_state = kern_fmt1->state_table.header.stateArray + (FT_Byte)initial_state;
  final_class = ( initial_state == GXL_START_OF_TEXT_STATE )
    ? GX_CLASS_END_OF_TEXT: GX_CLASS_END_OF_LINE;

  kernstack_init( &kernstack );
  while ( current_glyph <= glength )
    {
      FT_TRACE3(("  glyph id: %u, glyph position: %lu/%lu\n", 
		 current_glyph == glength? 0xFFFF: glyphs[current_glyph].gid,
		 current_glyph, glength ));

      /* glyph -> class */
      class_code = ( current_glyph == glength )
	? final_class: gx_StateTable_get_class ( &kern_fmt1->state_table,
						 glyphs[current_glyph].gid );
      FT_TRACE3(("  class code: %u current state: %u\n", class_code, current_state ));
      
      /* class -> entry */
      entry_subtable = gx_StateTable_get_entry_subtable ( &kern_fmt1->state_table,
							  current_state, 
							  class_code );

      /* action for entry */
      if ( entry_subtable->flags & GX_KERN_ACTION_PUSH )
	{
	  FT_TRACE3(("  Push[current_glyph %lu] %lu to the stack\n",
		     current_glyph, glyphs[current_glyph] ));
	  kernstack_push(&kernstack, current_glyph);
	}

      /* action */
      value_offset = entry_subtable->flags & GX_KERN_ACTION_VALUE_OFFSET;
      if ( value_offset )
	{
	  value_index = ( value_offset - kern_fmt1->valueTable ) 
	    / sizeof (*(kern_fmt1->values));
	  
	  FT_ASSERT ( value_index < kern_fmt1->nValues );

	  value_index--;
	  do {
	    value_index++;
	    FT_ASSERT ( value_index < kern_fmt1->nValues );
	    
	    raw_value     = kern_fmt1->values[value_index];
	    if ( raw_value & GX_KERN_VALUE_RESET_CROSS_STREAM )
	      {
		FT_TRACE3(("  Reset cross stream kerning\n"));
		value 		   = -total_cross_stream;
		total_cross_stream = 0;
	      }
	    else if (value == GX_KERN_VALUE_END_LIST)
	      value = 0;
	    else
	      {
		value = raw_value;
		if ( cross_stream )
		  total_cross_stream += value;
	      }
	    
	    applied_glyph = kernstack_pop( &kernstack );
	    if ( cross_stream )
	      {
		if ( dir == FTL_HORIZONTAL )
		  target = &kerning[applied_glyph + 1].y;
		else
		  target = &kerning[applied_glyph + 1].x;
	      }
	    else
	      {
		if ( dir == FTL_HORIZONTAL )
		  target = &kerning[applied_glyph + 1].x;
		else
		  target = &kerning[applied_glyph + 1].y;
	      }

	    *target =  value;
	  } while ( !( raw_value & GX_KERN_VALUE_END_LIST ) );
	}
 
      /* advance */
      if ( !(entry_subtable->flags & GX_KERN_ACTION_DONT_ADVANCE ) )
	{
	  FT_TRACE3(("  index++.\n"));
	  current_glyph++;
	}

      /* new state */
      current_state = entry_subtable->newState;
    }
  FT_TRACE2(("Leave contextual kerning\n"));
  return FT_Err_Ok;
}

/* END */
