/*
 * This little program is used to parse the FreeType headers and
 * find the declaration of all public APIs.  This is easy, because
 * they all look like the following:
 *
 *   FT_EXPORT( return_type )
 *   function_name( function arguments );
 *
 * You must pass the list of header files as arguments.  Wildcards are
 * accepted if you are using GCC for compilation (and probably by
 * other compilers too).
 *
 * Author: FreeType team, 2005-2019
 *
 * This code is explicitly placed into the public domain.
 *
 */

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>

#define  PROGRAM_NAME     "apinames"
#define  PROGRAM_VERSION  "0.3"

#define  LINEBUFF_SIZE  1024


typedef enum  OutputFormat_
{
  OUTPUT_LIST = 0,      /* output the list of names, one per line             */
  OUTPUT_WINDOWS_DEF,   /* output a Windows .DEF file for Visual C++ or Mingw */
  OUTPUT_BORLAND_DEF,   /* output a Windows .DEF file for Borland C++         */
  OUTPUT_WATCOM_LBC,    /* output a Watcom Linker Command File                */
  OUTPUT_NETWARE_IMP,   /* output a NetWare ImportFile                        */
  OUTPUT_GNU_VERMAP     /* output a version map for GNU or Solaris linker     */

} OutputFormat;


static void
panic( const char*  message )
{
  fprintf( stderr, "PANIC: %s\n", message );
  exit(2);
}


typedef struct  NameRec_
{
  char*         name;
  unsigned int  hash;

} NameRec, *Name;


static Name  the_names;
static int   num_names;
static int   max_names;


static void
names_add( const char*  name,
           const char*  end )
{
  unsigned int  h;
  int           nn, len;
  Name          nm;


  if ( end <= name )
    return;

  /* compute hash value */
  len = (int)( end - name );
  h   = 0;

  for ( nn = 0; nn < len; nn++ )
    h = h * 33 + name[nn];

  /* check for an pre-existing name */
  for ( nn = 0; nn < num_names; nn++ )
  {
    nm = the_names + nn;

    if ( (int)nm->hash                 == h &&
         memcmp( name, nm->name, len ) == 0 &&
         nm->name[len]                 == 0 )
      return;
  }

  /* add new name */
  if ( num_names >= max_names )
  {
    max_names += ( max_names >> 1 ) + 4;
    the_names  = (NameRec*)realloc( the_names,
                                    sizeof ( the_names[0] ) * max_names );
    if ( !the_names )
      panic( "not enough memory" );
  }
  nm = &the_names[num_names++];

  nm->hash = h;
  nm->name = (char*)malloc( len + 1 );
  if ( !nm->name )
    panic( "not enough memory" );

  memcpy( nm->name, name, len );
  nm->name[len] = 0;
}


static int
name_compare( const void*  name1,
              const void*  name2 )
{
  Name  n1 = (Name)name1;
  Name  n2 = (Name)name2;

  return strcmp( n1->name, n2->name );
}


static void
names_sort( void )
{
  qsort( the_names, (size_t)num_names,
         sizeof ( the_names[0] ), name_compare );
}


static void
names_dump( FILE*         out,
            OutputFormat  format,
            const char*   dll_name )
{
  int  nn;


  switch ( format )
  {
  case OUTPUT_WINDOWS_DEF:
    if ( dll_name )
      fprintf( out, "LIBRARY %s\n", dll_name );

    fprintf( out, "DESCRIPTION  FreeType 2 DLL\n" );
    fprintf( out, "EXPORTS\n" );

    for ( nn = 0; nn < num_names; nn++ )
      fprintf( out, "  %s\n", the_names[nn].name );

    break;

  case OUTPUT_BORLAND_DEF:
    if ( dll_name )
      fprintf( out, "LIBRARY %s\n", dll_name );

    fprintf( out, "DESCRIPTION  FreeType 2 DLL\n" );
    fprintf( out, "EXPORTS\n" );

    for ( nn = 0; nn < num_names; nn++ )
      fprintf( out, "  _%s\n", the_names[nn].name );

    break;

  case OUTPUT_WATCOM_LBC:
    {
      const char*  dot;
      char         temp[512];


      if ( !dll_name )
      {
        fprintf( stderr,
                 "you must provide a DLL name with the -d option!\n" );
        exit( 4 );
      }

      /* we must omit the `.dll' suffix from the library name */
      dot = strchr( dll_name, '.' );
      if ( dot )
      {
        int  len = dot - dll_name;


        if ( len > (int)( sizeof ( temp ) - 1 ) )
          len = sizeof ( temp ) - 1;

        memcpy( temp, dll_name, len );
        temp[len] = 0;

        dll_name = (const char*)temp;
      }

      for ( nn = 0; nn < num_names; nn++ )
        fprintf( out, "++_%s.%s.%s\n",
                      the_names[nn].name, dll_name, the_names[nn].name );
    }

    break;

  case OUTPUT_NETWARE_IMP:
    if ( dll_name )
      fprintf( out, "  (%s)\n", dll_name );

    for ( nn = 0; nn < num_names - 1; nn++ )
      fprintf( out, "  %s,\n", the_names[nn].name );
    fprintf( out, "  %s\n", the_names[num_names - 1].name );

    break;

  case OUTPUT_GNU_VERMAP:
    fprintf( out, "{\n\tglobal:\n" );

    for ( nn = 0; nn < num_names; nn++ )
      fprintf( out, "\t\t%s;\n", the_names[nn].name );

    fprintf( out, "\tlocal:\n\t\t*;\n};\n" );

    break;

  default:  /* LIST */
    for ( nn = 0; nn < num_names; nn++ )
      fprintf( out, "%s\n", the_names[nn].name );

    break;
  }
}


/* states of the line parser */

typedef enum  State_
{
  STATE_START = 0,  /* waiting for FT_EXPORT keyword and return type */
  STATE_TYPE        /* type was read, waiting for function name      */

} State;


static int
read_header_file( FILE*  file,
                  int    verbose )
{
  static char  buff[LINEBUFF_SIZE + 1];
  State        state = STATE_START;


  while ( !feof( file ) )
  {
    char*  p;


    if ( !fgets( buff, LINEBUFF_SIZE, file ) )
      break;

    p = buff;

    /* skip leading whitespace */
    while ( *p && ( *p == ' ' || *p == '\\' ) )
      p++;

    /* skip empty lines */
    if ( *p == '\n' || *p == '\r' )
      continue;

    switch ( state )
    {
    case STATE_START:
      if ( memcmp( p, "FT_EXPORT(", 10 ) != 0 )
        break;

      p += 10;
      for (;;)
      {
        if ( *p == 0 || *p == '\n' || *p == '\r' )
          goto NextLine;

        if ( *p == ')' )
        {
          p++;
          break;
        }

        p++;
      }

      state = STATE_TYPE;

      /*
       * Sometimes, the name is just after `FT_EXPORT(...)', so skip
       * whitespace and fall-through if we find an alphanumeric character.
       */
      while ( *p == ' ' || *p == '\t' )
        p++;

      if ( !isalpha( *p ) )
        break;

      /* fall-through */

    case STATE_TYPE:
      {
        char*   name = p;


        while ( isalnum( *p ) || *p == '_' )
          p++;

        if ( p > name )
        {
          if ( verbose )
            fprintf( stderr, ">>> %.*s\n", (int)( p - name ), name );

          names_add( name, p );
        }

        state = STATE_START;
      }

      break;

    default:
      ;
    }

NextLine:
    ;
  } /* end of while loop */

  return 0;
}


static void
usage( void )
{
  static const char* const  format =
    "%s %s: extract FreeType API names from header files\n"
    "\n"
    "This program extracts the list of public FreeType API functions.\n"
    "It receives a list of header files as an argument and\n"
    "generates a sorted list of unique identifiers in various formats.\n"
    "\n"
    "usage: %s header1 [options] [header2 ...]\n"
    "\n"
    "options:   -       parse the contents of stdin, ignore arguments\n"
    "           -v      verbose mode, output sent to standard error\n"
    "           -oFILE  write output to FILE instead of standard output\n"
    "           -dNAME  indicate DLL file name, 'freetype.dll' by default\n"
    "           -w      output .DEF file for Visual C++ and Mingw\n"
    "           -wB     output .DEF file for Borland C++\n"
    "           -wW     output Watcom Linker Response File\n"
    "           -wN     output NetWare Import File\n"
    "           -wL     output version map for GNU or Solaris linker\n"
    "\n";

  fprintf( stderr,
           format,
           PROGRAM_NAME,
           PROGRAM_VERSION,
           PROGRAM_NAME );

  exit( 1 );
}


int
main( int                 argc,
      const char* const*  argv )
{
  int           from_stdin   = 0;
  int           verbose      = 0;
  OutputFormat  format       = OUTPUT_LIST;  /* the default */
  FILE*         out          = stdout;
  const char*   library_name = NULL;


  if ( argc < 2 )
    usage();

  /* `-' used as a single argument means read source file from stdin */
  while ( argc > 1 && argv[1][0] == '-' )
  {
    const char*  arg = argv[1];


    switch ( arg[1] )
    {
    case 'v':
      verbose = 1;

      break;

    case 'o':
      if ( arg[2] == 0 )
      {
        if ( argc < 2 )
          usage();

        arg = argv[2];
        argv++;
        argc--;
      }
      else
        arg += 2;

      out = fopen( arg, "wt" );
      if ( !out )
      {
        fprintf( stderr, "could not open '%s' for writing\n", arg );
        exit( 3 );
      }

      break;

    case 'd':
      if ( arg[2] == 0 )
      {
        if ( argc < 2 )
          usage();

        arg = argv[2];
        argv++;
        argc--;
      }
      else
        arg += 2;

      library_name = arg;

      break;

    case 'w':
      format = OUTPUT_WINDOWS_DEF;

      switch ( arg[2] )
      {
      case 'B':
        format = OUTPUT_BORLAND_DEF;
        break;

      case 'W':
        format = OUTPUT_WATCOM_LBC;
        break;

      case 'N':
        format = OUTPUT_NETWARE_IMP;
        break;

      case 'L':
        format = OUTPUT_GNU_VERMAP;
        break;

      case 0:
        break;

      default:
        usage();
      }

      break;

    case 0:
      from_stdin = 1;

      break;

    default:
      usage();
    }

    argc--;
    argv++;

  } /* end of while loop */

  if ( from_stdin )
    read_header_file( stdin, verbose );
  else
  {
    for ( --argc, argv++; argc > 0; argc--, argv++ )
    {
      FILE*  file = fopen( argv[0], "rb" );


      if ( !file )
        fprintf( stderr, "unable to open '%s'\n", argv[0] );
      else
      {
        if ( verbose )
          fprintf( stderr, "opening '%s'\n", argv[0] );

        read_header_file( file, verbose );
        fclose( file );
      }
    }
  }

  if ( num_names == 0 )
    panic( "could not find exported functions\n" );

  names_sort();
  names_dump( out, format, library_name );

  if ( out != stdout )
    fclose( out );

  return 0;
}


/* END */
