/*
    gendef - Generate list of exported symbols from a Portable Executable.
    Copyright (C) 2009-2016  mingw-w64 project

    This program is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation, either version 3 of the License, or
    (at your option) any later version.

    This program is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with this program.  If not, see <http://www.gnu.org/licenses/>.
*/
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#include <stddef.h>
#include <stdio.h>
#include <stdlib.h>
#include <memory.h>
#include <string.h>
#include "compat_string.h"
#include "gendef.h"
#include "fsredir.h"
#ifdef HAVE_LIBMANGLE
#include <libmangle.h>
#endif

#define ENABLE_DEBUG 0

#if ENABLE_DEBUG == 1
#define PRDEBUG(ARG...)  fprintf(stderr,ARG)
#else
#define PRDEBUG(ARG...) do { } while(0)
#endif

static void decode_mangle (FILE *fp, const char *n);
static int load_pep (void);
static void do_pedef (void);
static void do_pepdef (void);
static void do_import_read32 (uint32_t va_imp, uint32_t sz_imp);
static void do_export_read (uint32_t va_exp,uint32_t sz_exp,int be64);
static void add_export_list (uint32_t ord,uint32_t func,const char *name, const char *forward,int be64,int beData);
static void dump_def (void);
static int disassembleRet (uint32_t func,uint32_t *retpop,const char *name, sImportname **ppimpname, int *seen_ret);
static size_t getMemonic (int *aCode,uint32_t pc,volatile uint32_t *jmp_pc,const char *name, sImportname **ppimpname);

static sImportname *imp32_add (const char *dll, const char *name, uint32_t addr, uint16_t ord);
static void imp32_free (void);
static sImportname *imp32_findbyaddress (uint32_t addr);

static sImportname *theImports = NULL;

static void *map_va (uint32_t va);
static int is_data (uint32_t va);
static int is_reloc (uint32_t va);
static int has_atdecoration (void);

static int disassembleRetIntern (uint32_t pc, uint32_t *retpop, sAddresses *seen, sAddresses *stack,
				 int *hasret, int *atleast_one, const char *name, sImportname **ppimpname);
static sAddresses*init_addr (void);
static void dest_addr (sAddresses *ad);
static int push_addr (sAddresses *ad,uint32_t val);
static int pop_addr (sAddresses *ad,uint32_t *val);

static sExportName *gExp = NULL;
static sExportName *gExpTail = NULL;
char *fninput;
char *fnoutput;
char *fndllname;

size_t gDta_size;
unsigned char *gDta;
PIMAGE_DOS_HEADER gMZDta;
PIMAGE_NT_HEADERS32 gPEDta;
PIMAGE_NT_HEADERS64 gPEPDta;

#ifdef REDIRECTOR
static int use_redirector = 0; /* Use/Disable FS redirector */
#endif

static int std_output = 0;
static int assume_stdcall = 0; /* Set to one, if function symbols should be assumed to have stdcall.  */
static int no_forward_output = 0; /* Set to one, if in .def files forwarders shouldn't be displayed.  */

static Gendefopts *chain_ptr = NULL;
 __attribute__((noreturn)) static void show_usage (void);
static int opt_chain (const char *, const char *);

static int
opt_chain (const char *opts, const char *next)
{
  static Gendefopts *prev, *current;
  char *r1, *r2;
  
  if (!strncmp (opts, "-", 2))
    {
      std_output = 1;
      return 0;
    }
  if (!strcmp (opts, "--help") || !strcmp (opts, "-h"))
    {
      show_usage();
      return 0;
    }
  if (!strcmp (opts, "--assume-stdcall") || !strcmp (opts, "-a"))
    {
      assume_stdcall = 1;
      return 0;
    }
  if (!strcmp (opts, "--include-def-path") || !strcmp (opts, "-I"))
    {
      if (!next)
        {
	  fprintf (stderr, "Error: %s expects path as next arguement.", opts);
	  return 0;
        }
      gendef_addpath_def (next);
      return 1;
    }
  if (!strcmp (opts, "--no-include-current-dir"))
    {
      gendef_no_include_current_dir ();
      return 0;
    }
  if (!strcmp (opts, "--no-forward-output") || !strcmp (opts, "-f"))
    {
      no_forward_output = 1;
      return 0;
    }

#ifdef REDIRECTOR
  if (!strcmp (opts, "--disable-fs-redirector") || !strcmp (opts, "-r"))
    {
      use_redirector = 1;
      return 0;
    }
#endif

  current = malloc (sizeof(Gendefopts));
  if (current)
    {
      memset (current, 0, sizeof (Gendefopts));
      current->next = NULL;

      if (!prev)
        chain_ptr = current;
      else
        prev->next = current;
      r1 = strrchr (opts,'/');
      r2 = strrchr (opts,'\\');
      current->fninput = strdup (opts);
      
      if (!r1 && r2 != NULL)
        r1 = r2 + 1;
      else if(r1 == NULL && r2 == NULL)
        r1 = current->fninput;
      else if (r2 != NULL && r1 != NULL && r1 < r2)
        r1 = r2 + 1;
      else
        r1++;
      current->fnoutput = (char *) malloc (strlen (current->fninput) + 5);
      strcpy (current->fnoutput,r1);

      r1 = strrchr (current->fnoutput,'.');
      if (r1)
        strcpy (r1,".def");
      else
        strcat (current->fnoutput,".def");
      prev = current;
   }
  return 0;
}

void
show_usage (void)
{
  fprintf (stderr, "Usage: gendef [OPTION]... [DLL]...\n");
  fprintf (stderr, "Dumps DLL exports information from PE32/PE32+ executables\n");
  fprintf (stderr, "\n");
  fprintf (stderr, "Options:\n"
    "  -                        Dump to stdout\n"
    "  -h, --help               Show this help.\n"
    "  -a, --assume-stdcall     Assume functions with ambiguous call\n"
    "                           convention as stdcall.\n"
    "  -I, --include-def-path <path>\n"
    "                           Add additional search paths to find\n"
    "                           hint .def files.\n"
    "  --no-include-current-dir Don't search current directory to find\n"
    "                           hint .def files.\n"
    "  -f, --no-forward-output  Don't output forwarders in .def file\n"
#ifdef REDIRECTOR
    "  -r, --disable-fs-redirector\n"
    "                           Disable Win64 FS redirection, for 32-bit\n"
    "                           gendef on 64-bit Windows\n"
#endif
  );
  fprintf (stderr, "\n");
  fprintf (stderr, "Usage example: \n"
                   "  By default, the output files are named after their DLL counterparts\n"
                   "  gendef MYDLL.DLL     Produces MYDLL.def\n"
                   "  gendef - MYDLL.DLL   Prints the exports to stdout\n");
  fprintf (stderr, "\nVersion %s\n", VERSION);
  fprintf (stderr, "\nReport bugs to <mingw-w64-public@lists.sourceforge.net>\n");
  exit (0);
}

int main(int argc,char **argv)
{
  int i;
  Gendefopts *opt, *next;

  if (argc < 2)
  {
    show_usage ();
    return 0;
  }

  for (i = 1; i < argc; i++)
    i += opt_chain (argv[i], ((i+1) < argc ? argv[i+1] : NULL));
#ifdef REDIRECTOR
  doredirect(use_redirector);
#endif
  opt = chain_ptr;
  while (opt)
    {
      fninput = opt->fninput;
      fnoutput = opt->fnoutput;

      if (load_pep ())
        {
	  if (gPEDta || gPEPDta)
	    {
	      if (gPEDta)
		do_pedef ();
	      else
		do_pepdef ();
	      dump_def ();
	    }
	}
      if (fndllname)
	free (fndllname);
      fndllname = NULL;
      if (gDta)
	{
	  free (gDta);
	  gDta = NULL;
	}
      next = opt->next;
      free(opt->fninput);
      free(opt->fnoutput);
      free(opt);
      opt = next;
    }
  imp32_free ();
  return 0;
}

static int
load_pep (void)
{
  FILE *fp = fopen (fninput, "rb");

  if (!fp)
    {
      fprintf (stderr, "*** [%s] failed to open()\n", fninput);
      return 0;
    }
  fseek (fp, 0, SEEK_END);
  gDta_size = (size_t) ftell (fp);
  if (gDta_size > 0) {
    fseek (fp,0,SEEK_SET);
    gDta = (unsigned char *) malloc (gDta_size + 1);
    if (gDta)
      {
        if (fread (gDta, gDta_size, 1, fp) != 1)
	  {
	    free (gDta);
	    gDta = NULL;
	  }
	else
          gDta[gDta_size] = 0;
    }
  }
  fclose (fp);
  if (!gDta)
    {
      fprintf (stderr, "*** [%s] unable to allocate %lu bytes\n", fninput,
	       (unsigned long) gDta_size);
      return 0;
    }
  gMZDta = (PIMAGE_DOS_HEADER) gDta;
  if (gDta_size < sizeof(IMAGE_DOS_HEADER) || gDta[0]!='M' || gDta[1]!='Z'
      || gMZDta->e_lfanew <= 0
      || gMZDta->e_lfanew >= (int32_t) gDta_size)
  {
    fprintf(stderr,"*** [%s] not a PE(+) file\n", fninput);
    free(gDta);
    gDta = NULL;
    return 0;
  }
  gPEDta = (PIMAGE_NT_HEADERS32) &gDta[gMZDta->e_lfanew];
  gPEPDta = (PIMAGE_NT_HEADERS64) gPEDta;
  if (gPEDta->Signature != IMAGE_NT_SIGNATURE)
    {
      fprintf (stderr, "*** [%s] no PE(+) signature\n", fninput);
      free (gDta);
      gDta = NULL;
      gPEPDta = NULL;
      gPEDta = NULL;
      return 0;
    }
  if (gPEDta->FileHeader.SizeOfOptionalHeader >= offsetof(IMAGE_OPTIONAL_HEADER32, DataDirectory)
      && gPEDta->OptionalHeader.Magic == IMAGE_NT_OPTIONAL_HDR32_MAGIC)
    {
      gPEPDta = NULL;
      fprintf (stderr, " * [%s] Found PE image\n", fninput);
    }
  else if (gPEDta->FileHeader.SizeOfOptionalHeader >= offsetof(IMAGE_OPTIONAL_HEADER32, DataDirectory)
      && gPEDta->OptionalHeader.Magic == 0 && gPEDta->FileHeader.Machine == 0x014c /* IMAGE_FILE_MACHINE_I386 */)
    {
      gPEPDta = NULL;
      fprintf (stderr, " * [%s] Found PE image for I386 with zeroed NT magic\n", fninput);
    }
  else if (gPEPDta->FileHeader.SizeOfOptionalHeader >= offsetof(IMAGE_OPTIONAL_HEADER64, DataDirectory)
    && gPEPDta->OptionalHeader.Magic == IMAGE_NT_OPTIONAL_HDR64_MAGIC)
    {
      gPEDta = NULL;
      fprintf (stderr, " * [%s] Found PE+ image\n", fninput);
    }
  else
    {
      free (gDta);
      gDta = NULL;
      fprintf (stderr, "*** [%s] no PE(+) optional header\n", fninput);
      gPEPDta = NULL;
      gPEDta = NULL;
      return 0;
    }
  return 1;
}

static int
is_data (uint32_t va)
{
  PIMAGE_SECTION_HEADER sec;
  uint32_t sec_cnt,i;

  /* If export va is directly relocated, so it must be data.  */  
  if (is_reloc (va))
    return 1;
  
  if (gPEDta)
    {
      sec_cnt = gPEDta->FileHeader.NumberOfSections;
      sec = IMAGE_FIRST_SECTION(gPEDta);
    }
  else
    {
      sec_cnt = gPEPDta->FileHeader.NumberOfSections;
      sec = IMAGE_FIRST_SECTION(gPEPDta);
    }
  if (!sec)
    return 0;
  for (i = 0;i < sec_cnt;i++)
    {
      if (va >= sec[i].VirtualAddress && va < (sec[i].VirtualAddress+sec[i].Misc.VirtualSize))
        break;
    }
  if (i == sec_cnt)
    return 0; 
  if ((sec[i].Characteristics & (IMAGE_SCN_MEM_EXECUTE | IMAGE_SCN_CNT_CODE)) != 0)
    return 0;
  if ((sec[i].Characteristics & IMAGE_SCN_MEM_DISCARDABLE) != 0)
    return 1;
  if ((sec[i].Characteristics & IMAGE_SCN_MEM_READ) ==0)
    return 0;
  if ((sec[i].Characteristics & (IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_CNT_UNINITIALIZED_DATA | IMAGE_SCN_LNK_COMDAT)) != 0)
    return 1;
  return 1;
}

static int
is_reloc (uint32_t va)
{
  uint32_t va_rel = 0;
  uint32_t sz_rel = 0;
  uint32_t pos;
  unsigned char *p;
  PIMAGE_BASE_RELOCATION brel;

  if (gPEDta)
    {
      if (gPEDta->OptionalHeader.NumberOfRvaAndSizes > IMAGE_DIRECTORY_ENTRY_BASERELOC)
        {
          va_rel = gPEDta->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress;
          sz_rel = gPEDta->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC].Size;
        }
    }
  else
    {
      if (gPEPDta->OptionalHeader.NumberOfRvaAndSizes > IMAGE_DIRECTORY_ENTRY_BASERELOC)
        {
          va_rel = gPEPDta->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress;
          sz_rel = gPEPDta->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC].Size;
        }
    }
  if (va_rel == 0 || sz_rel < IMAGE_SIZEOF_BASE_RELOCATION)
    return 0;
  p = (unsigned char *) map_va (va_rel);
  for (pos = 0; pos < sz_rel;)
    {
      uint16_t *r;
      uint32_t nums, j;
      if ((sz_rel - pos) < IMAGE_SIZEOF_BASE_RELOCATION)
        break;
      brel = (PIMAGE_BASE_RELOCATION) &p[pos];
      if (brel->SizeOfBlock == 0)
         break;
      pos += IMAGE_SIZEOF_BASE_RELOCATION;
      nums = (brel->SizeOfBlock - IMAGE_SIZEOF_BASE_RELOCATION) / 2;
      r = (uint16_t *) &p[pos];
      if (va >= brel->VirtualAddress && va < (brel->VirtualAddress + 0x1008))
        {
          for (j = 0; j < nums; j++)
            {
              uint32_t relsz = 0;
              uint32_t offs = (uint32_t) (r[j] & 0xfff) + brel->VirtualAddress;
              uint16_t typ = (r[j] >> 12) & 0xf;
              if (typ == IMAGE_REL_BASED_HIGHADJ)
                j++;
              switch (typ)
                {
                case IMAGE_REL_BASED_HIGHLOW:
                  relsz = 4;
                  break;
                case IMAGE_REL_BASED_DIR64:
                  relsz = 8;
                  break;
                }
              if (relsz != 0 && va >= offs && va < (offs + relsz))
                return 1;
            }
        }
      pos += (brel->SizeOfBlock - IMAGE_SIZEOF_BASE_RELOCATION);
    }
  return 0;
}

static void *
map_va (uint32_t va)
{
  PIMAGE_SECTION_HEADER sec;
  uint32_t sec_cnt,sz,i;
  char *dptr;

  if (gPEDta)
    {
      sec_cnt = gPEDta->FileHeader.NumberOfSections;
      sec = IMAGE_FIRST_SECTION(gPEDta);
    }
  else
    {
      sec_cnt = gPEPDta->FileHeader.NumberOfSections;
      sec = IMAGE_FIRST_SECTION(gPEPDta);
    }
  for (i = 0;i < sec_cnt;i++)
    {
      sz = sec[i].Misc.VirtualSize;
      if (!sz) sz = sec[i].SizeOfRawData;
      if (va >= sec[i].VirtualAddress && va < (sec[i].VirtualAddress+sz))
        {
          dptr = (char *) &gDta[va-sec[i].VirtualAddress+sec[i].PointerToRawData];
          return (void *)dptr;
        }
    }
  return NULL;
}

/* For pep we can take the exports itself, there is no additional decoration necessary.  */
static void
do_pepdef (void)
{
  uint32_t va_exp = 0;
  uint32_t sz_exp = 0;

  if (gPEPDta->OptionalHeader.NumberOfRvaAndSizes > IMAGE_DIRECTORY_ENTRY_EXPORT)
    {
      va_exp = gPEPDta->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress;
      sz_exp = gPEPDta->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].Size;
    }

  do_export_read (va_exp, sz_exp, 1);
}

static void
do_pedef (void)
{
  uint32_t va_exp = 0;
  uint32_t sz_exp = 0;
  uint32_t va_imp = 0;
  uint32_t sz_imp = 0;

  if (gPEDta->OptionalHeader.NumberOfRvaAndSizes > IMAGE_DIRECTORY_ENTRY_EXPORT)
    {
      va_exp = gPEDta->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress;
      sz_exp = gPEDta->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].Size;
    }

  if (gPEDta->OptionalHeader.NumberOfRvaAndSizes > IMAGE_DIRECTORY_ENTRY_IMPORT)
    {
      va_imp = gPEDta->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress;
      sz_imp = gPEDta->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].Size;
    }

  imp32_free ();
  do_import_read32 (va_imp, sz_imp);
  do_export_read (va_exp, sz_exp, 0);
}

static void
do_import_read32 (uint32_t va_imp, uint32_t sz_imp)
{
  IMAGE_IMPORT_DESCRIPTOR *pid;
  if (!sz_imp || !va_imp)
    return;
  pid = (IMAGE_IMPORT_DESCRIPTOR *) map_va (va_imp);
  while (pid != NULL && sz_imp >= 20 && pid->Name != 0 && pid->OriginalFirstThunk != 0)
    {
      uint32_t index = 0;
      PIMAGE_THUNK_DATA32 pIAT;
      PIMAGE_THUNK_DATA32 pFT;
      char *imp_name = (char *) map_va (pid->Name);

      for (;;) {
	char *fctname;
	pIAT = (PIMAGE_THUNK_DATA32) map_va (pid->OriginalFirstThunk + index);
	pFT = (PIMAGE_THUNK_DATA32) map_va (pid->FirstThunk + index);
	if (pIAT->u1.Ordinal == 0 || pFT->u1.Ordinal == 0)
	  break;
	if (IMAGE_SNAP_BY_ORDINAL32 (pIAT->u1.Ordinal))
	  fctname = NULL;
	else
	  fctname = (char *) map_va (pIAT->u1.Function + 2);
	if (fctname)
	  imp32_add (imp_name, fctname,
	  //pid->OriginalFirstThunk + index + gPEDta->OptionalHeader.ImageBase,
	  pid->FirstThunk + index + gPEDta->OptionalHeader.ImageBase,
	    *((uint16_t *) map_va (pIAT->u1.Function)));
	index += 4;
      }
      sz_imp -= 20;
      va_imp += 20;
      if (sz_imp >= 20)
	pid = (IMAGE_IMPORT_DESCRIPTOR *) map_va (va_imp);
    }
}

static sImportname *
imp32_findbyaddress (uint32_t addr)
{
  sImportname *h = theImports;
  while (h != NULL && h->addr_iat != addr)
    h = h->next;
  return h;
}

static void
imp32_free (void)
{
  while (theImports != NULL)
    {
      sImportname *h = theImports;
      theImports = theImports->next;
      if (h->dll)
	free (h->dll);
      if (h->name)
	free (h->name);
      free (h);
    }
}

static sImportname *
imp32_add (const char *dll, const char *name, uint32_t addr, uint16_t ord)
{
  sImportname *n = (sImportname *) malloc (sizeof (sImportname));
  memset (n, 0, sizeof (sImportname));
  n->dll = strdup (dll);
  n->name = strdup (name);
  n->ord = ord;
  n->addr_iat = addr;
  n->next = theImports;
  theImports = n;
  return n;
}

static void
do_export_read (uint32_t va_exp, uint32_t sz_exp, int be64)
{
  uint32_t i;
  PIMAGE_EXPORT_DIRECTORY exp_dir;
  uint32_t *functions;
  uint16_t *ordinals;
  uint32_t *name;

  if (va_exp == 0 || sz_exp == 0)
    return;
  exp_dir = (PIMAGE_EXPORT_DIRECTORY) map_va (va_exp);
  PRDEBUG(" * export directory at VA = 0x%x size=0x%x\n", (unsigned int) va_exp, (unsigned int) sz_exp);
  fndllname = strdup ((char *) map_va (exp_dir->Name));
  PRDEBUG(" * Name: %s\n * Base: %u\n", fndllname, (unsigned int) exp_dir->Base);
  functions = (uint32_t *) map_va (exp_dir->AddressOfFunctions);
  ordinals = (uint16_t *) map_va (exp_dir->AddressOfNameOrdinals);
  name = (uint32_t *) map_va (exp_dir->AddressOfNames);
  
  for (i = 0;i < exp_dir->NumberOfFunctions;i++)
    {
      uint32_t entryPointRVA = functions[i];
      uint32_t j;
      char *fname;
      uint32_t ord;
      fname = NULL;
      if (!entryPointRVA)
        continue;
      ord = i + exp_dir->Base;
      for (j = 0;j < exp_dir->NumberOfNames;j++)
        if (ordinals[j]==i)
          fname = (char *) map_va (name[j]);
      if (entryPointRVA >= va_exp && entryPointRVA <= (va_exp + sz_exp))
        add_export_list (ord, 0, fname,(char *) map_va (entryPointRVA), be64, 0);
      else
        add_export_list(ord, entryPointRVA, fname, NULL, be64, is_data (entryPointRVA));
    }
}

static void
add_export_list(uint32_t ord,uint32_t func,const char *name, const char *forward,int be64,int beData)
{
  sExportName *exp = NULL;

  if (!name)
    name = "";
  if (!forward)
    forward = "";
  exp = (sExportName *) malloc (sizeof (sExportName) + strlen (name) + strlen (forward) + 2);
  if (!exp)
    return;
  exp->name = (char *) &exp[1];
  exp->forward = exp->name + strlen (name) + 1;
  strcpy (exp->name, name);
  strcpy (exp->forward, forward);
  exp->next = NULL;
  exp->ord = ord;
  exp->func = func;
  exp->be64 = be64;
  exp->beData = beData;
  exp->retpop = (uint32_t)-1;
  if (gExpTail)
    gExpTail->next = exp;
  else
    gExp = exp;
  gExpTail = exp;
}

static void
dump_def (void)
{
  sExportName *exp;
  FILE *fp;

  if (!fndllname || gExp == NULL)
    return;
  if (!std_output)
    fp = fopen(fnoutput,"wt");
  else
    fp = stdout;
  if(!fp) {
    fprintf(stderr," * failed to create %s ...\n",fnoutput);
    return;
  }
  fprintf (fp,";\n; Definition file of %s\n; Automatic generated by gendef %s\n; written by Kai Tietz 2008\n; The def file has to be processed by --kill-at (-k) option of dlltool or ld\n;\n",
    fndllname, VERSION);
  fprintf (fp,"LIBRARY \"%s\"\nEXPORTS\n",fndllname);
  while ((exp = gExp) != NULL)
    {
      sImportname *pimpname;
      int seen_ret;
      seen_ret = 1;
      gExp = exp->next;
      int name_has_at_suffix = 0;
      int name_has_fastcall = 0;
      if (exp->name[0] == '?' && exp->name[1] == '?')
        {
          if (!strncmp (exp->name, "??_7", 4))
	    exp->beData = 1;
        }
      pimpname = NULL;
      if (!exp->beData && !exp->be64 && exp->func != 0)
	{
	  seen_ret = 0;
	  exp->beData = disassembleRet (exp->func, &exp->retpop, exp->name, &pimpname, &seen_ret);
        }
      if (!exp->be64 && exp->retpop == (uint32_t) -1 && pimpname)
	{
	  int isD = 0;
	  uint32_t at = 0;
	  if (gendef_getsymbol_info (pimpname->dll, pimpname->name, &isD, &at))
	    {
	      exp->beData = isD;
	      if (!isD)
		exp->retpop = at;
	    }
	}
      else if (exp->func == 0 && !exp->beData)
	{
	  int isD = 0;
	  uint32_t at = 0;
	  if (gendef_getsymbol_info (exp->forward, NULL, &isD, &at))
	    {
	      exp->beData = isD;
	      if (!isD)
	        exp->retpop = at;
	    }
	}

      if (exp->be64)
        exp->retpop = 0;

      if (exp->name[0] == '?')
        {
          decode_mangle (fp, exp->name);
        }

      if ((exp->name[0] == '_' || exp->name[0] == '@') && !exp->be64 && has_atdecoration())
        {
          char at_suffix[12];
          unsigned int retpop = exp->retpop != (uint32_t) -1 ? exp->retpop : 0;
          int name_len = strlen(exp->name);
          if (exp->name[0] == '_')
            {
              int at_suffix_len = sprintf(at_suffix, "@%u", retpop);
              if (name_len > at_suffix_len && memcmp(&exp->name[name_len-at_suffix_len], at_suffix, at_suffix_len) == 0)
                name_has_at_suffix = 1;
            }
          else if (exp->name[0] == '@')
            {
              if (retpop == 0)
                {
                  if (name_len > 2 && exp->name[name_len-2] == '@' && (exp->name[name_len-1] == '0' || exp->name[name_len-1] == '4' || exp->name[name_len-1] == '8'))
                    name_has_fastcall = 1;
                }
              else
                {
                  int at_suffix_len = sprintf(at_suffix, "@%u", retpop+8);
                  if (name_len > at_suffix_len && memcmp(&exp->name[name_len-at_suffix_len], at_suffix, at_suffix_len) == 0)
                    name_has_fastcall = 1;
                }
            }
        }
      if (exp->name[0] == 0)
        fprintf (fp, "ord_%u", (unsigned int) exp->ord);
      else
        {
          const char *quote = strchr (exp->name, '.') ? "\"" : "";
          const char *import_name = exp->name;
          if (name_has_at_suffix)
            import_name++;
          fprintf (fp, "%s%s%s", quote, import_name, quote);
        }

      if (exp->retpop != (uint32_t) -1 && !exp->be64 && has_atdecoration())
        {
          if (exp->name[0]=='?')
            fprintf(fp," ; has WINAPI (@%u)", (unsigned int) exp->retpop);
          else if (!name_has_at_suffix && !name_has_fastcall)
            fprintf(fp,"@%u", (unsigned int) exp->retpop);
        }
      if (exp->func == 0 && no_forward_output == 0)
	fprintf (fp, " = %s", exp->forward);
      if (exp->name[0] == 0)
        fprintf(fp," @%u NONAME", (unsigned int) exp->ord);
      if (exp->beData)
        fprintf(fp," DATA");
      if (name_has_at_suffix || name_has_fastcall)
        {
          const char *quote = strchr (exp->name, '.') ? "\"" : "";
          fprintf(fp, " == %s%s%s", quote, exp->name, quote);
        }

      if (exp->retpop != (uint32_t) -1 || (exp->retpop == 0 && exp->be64) || !has_atdecoration ())
	{
	}
      else if (pimpname)
        {
	  fprintf (fp, " ; Check!!! return value is from %s in %s (ordinal %u)",
	    pimpname->name, pimpname->dll, pimpname->ord);
        }
      else if (exp->func == 0 && !exp->beData)
	{
	  fprintf (fp, " ; Check!!! forwards to %s", exp->forward);
	}
      else if (seen_ret == 0 && !exp->beData)
        {
	  fprintf (fp, " ; Check!!! Couldn't determine function argument count. Function doesn't return.");
        }
      fprintf(fp,"\n");
      free (exp);
    }
  gExpTail=NULL;
  if (!std_output)
    fclose(fp);
}

static sAddresses *
init_addr (void)
{
  sAddresses *r = (sAddresses*) malloc (sizeof (sAddresses));
  r->max = 8;
  r->cnt = 0;
  r->ptrs = (uint32_t *) malloc (sizeof (uint32_t) * 8);
  r->idx = 0;
  return r;
}

static void
dest_addr (sAddresses *ad)
{
  free (ad->ptrs);
  free (ad);
}

static int
push_addr (sAddresses *ad, uint32_t val)
{
  uint32_t i;

  for (i = 0;i < ad->cnt; i++)
    {
      if (ad->ptrs[i] == val)
        return 0;
    }
  if (ad->max == ad->cnt)
    {
      uint32_t *p = (uint32_t *) malloc (sizeof (uint32_t) * (ad->max + 8));

      memcpy (p, ad->ptrs, sizeof (uint32_t) * ad->max);
      ad->max += 8;
      free (ad->ptrs);
      ad->ptrs = p;
    }
  ad->ptrs[ad->cnt++] = val;
  return 1;
}

static int
pop_addr (sAddresses *ad, uint32_t *val)
{
  if (!ad || ad->idx == ad->cnt)
    return 0;
  ad->idx++;
  *val = ad->ptrs[ad->idx-1];
  return 1;
}

static int
has_atdecoration (void)
{
  return (gPEDta && gPEDta->FileHeader.Machine == 0x014c /* IMAGE_FILE_MACHINE_I386 */);
}

/* exp->beData */
static int
disassembleRet (uint32_t func, uint32_t *retpop, const char *name, sImportname **ppimpname, int *seen_ret)
{
  sAddresses *seen = init_addr ();
  sAddresses *stack = init_addr ();
  uint32_t pc;
  int hasret = 0;
  int atleast_one = 0;

  if (!has_atdecoration())
  {
    *retpop = 0;
    return 0;
  }
  *retpop = (uint32_t) -1;
  push_addr (stack, func);

  while (!hasret && pop_addr (stack,&pc))
    {
      if (disassembleRetIntern (pc, retpop, seen, stack, &hasret, &atleast_one, name, ppimpname))
        break;
    }
  *seen_ret = hasret;
  dest_addr (seen);
  dest_addr (stack);
  return (atleast_one ? 0 : 1);
}

static int
disassembleRetIntern (uint32_t pc, uint32_t *retpop, sAddresses *seen, sAddresses *stack,
		      int *hasret, int *atleast_one, const char *name, sImportname **ppimpname)
{
  size_t sz = 0;
  int code = 0,break_it = 0;
  volatile uint32_t tojmp = 0;

  while(1)
    {
      if (!push_addr (seen, pc))
        return 0;
      sz = getMemonic (&code, pc, &tojmp, name, ppimpname) & 0xffffffff;
      if (!sz || code == c_ill)
        {
          PRDEBUG(" %s = 0x08%x ILL (%u) at least one==%d\n",name,
		  (unsigned int) pc, (unsigned int) sz,atleast_one[0]);
#if ENABLE_DEBUG == 1
      {
        unsigned char *ppc = (unsigned char *) map_va (pc);
        size_t i;

        fprintf (stderr, "%s(0x%x): ",name, (unsigned int) pc);
        for (i = 0;i < sz; i++)
          {
            fprintf (stderr, "%s0x%x", (i == 0 ? " ":","), ppc[i]);
          }
        fprintf (stderr, "\n");
      }
      exit (0);
#endif
          break;
        }
#if ENABLE_DEBUG == 1
      {
        unsigned char *ppc = (unsigned char *) map_va (pc);
        size_t i;

        fprintf (stderr, "%s(0x%x): ",name, (unsigned int) pc);
        for (i = 0;i < sz; i++)
          {
            fprintf (stderr, "%s0x%x", (i == 0 ? " ":","), ppc[i]);
          }
        fprintf (stderr, "\n");
      }
#endif
      atleast_one[0] += 1;
      break_it = 0;
      pc += sz;
      switch(code)
        {
        case c_jmpnjb: case c_jmpnjv:
          pc = tojmp;
          break;
        case c_jxx:
          push_addr (stack, tojmp);
          break;
        case c_jmpfap: case c_int3:
          break_it = 1;
          break;
        case c_iret: case c_retf: case c_retn:
          *hasret = 1;
          if (assume_stdcall)
            *retpop = 0;
          return 1;
        case c_retflw: case c_retnlw:
          *hasret = 1;
          *retpop = tojmp;
          return 1;
        }
      if (break_it)
        break;
    }

  return 0;
}

static int opMap2[256] = {
  c_EG,c_EG,c_EG,c_EG,c_1,c_1,c_ill,c_ill, /* 0x00-0x07 */
  c_1,c_1,c_ill,c_ill,c_ill,c_ill,c_ill,c_ill, /* 0x08-0x0f */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG, /* 0x10-0x17 */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG, /* 0x18-0x1f */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_ill,c_EG,c_ill, /* 0x20-0x27 */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG, /* 0x28-0x2f */
  c_1,c_1,c_1,c_1,c_1,c_1,c_ill,c_1, /* 0x30-0x37 */
  c_ill,c_ill,c_ill,c_ill,c_ill,c_ill,c_ill,c_ill, /* 0x38-0x3f */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG, /* 0x40-0x47 */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG, /* 0x48-0x4f */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG, /* 0x50-0x57 */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG, /* 0x58-0x5f */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG, /* 0x60-0x67 */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG, /* 0x68-0x6f */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG, /* 0x70-0x77 */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG, /* 0x78-0x7f */
  c_jxxv,c_jxxv,c_jxxv,c_jxxv,c_jxxv,c_jxxv,c_jxxv,c_jxxv, /* 0x80-0x87 */
  c_jxxv,c_jxxv,c_jxxv,c_jxxv,c_jxxv,c_jxxv,c_jxxv,c_jxxv, /* 0x88-0x8f */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG, /* 0x90-0x97 */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG, /* 0x98-0x9f */
  c_1,c_1,c_1,c_EG,c_EGlb,c_EG,c_ill,c_ill, /* 0xa0-0xa7 */
  c_1,c_1,c_1,c_EG,c_EGlb,c_EG,c_EG,c_EG, /* 0xa8-0xaf */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG, /* 0xb0-0xb7 */
  c_EG,c_1,c_EGlb,c_EG, c_EG,c_EG,c_EG,c_EG, /* 0xb8-0xbf */
  c_EG,c_EG,c_EGlb,c_EG,c_EGlb,c_EGlb,c_EGlb,c_EG, /* 0xc0-0xc7 */
  c_1,c_1,c_1,c_1,c_1,c_1,c_1,c_1, /* 0xc8-0xcf */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG, /* 0xd0-0xd7 */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG, /* 0xd8-0xdf */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG, /* 0xe0-0xe7 */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG, /* 0xe8-0xef */
  c_ill,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG, /* 0xf0-0xf7 */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_ill /* 0xf8-0xff */
};

static int opMap1[256] = {
  c_EG,c_EG,c_EG,c_EG,c_lb,c_lv,c_1,c_1, /* 0x00-0x07 */
  c_EG,c_EG,c_EG,c_EG,c_lb,c_lv,c_1,c_0f, /* 0x08-0x0f */
  c_EG,c_EG,c_EG,c_EG,c_lb,c_lv,c_1,c_1, /* 0x10-0x17 */
  c_EG,c_EG,c_EG,c_EG,c_lb,c_lv,c_1,c_1, /* 0x18-0x1f */
  c_EG,c_EG,c_EG,c_EG,c_lb,c_lv,c_1,c_1, /* 0x20-0x27 */
  c_EG,c_EG,c_EG,c_EG,c_lb,c_lv,c_1,c_1, /* 0x28-0x2f */
  c_EG,c_EG,c_EG,c_EG,c_lb,c_lv,c_1,c_1, /* 0x30-0x37 */
  c_EG,c_EG,c_EG,c_EG,c_lb,c_lv,c_1,c_1, /* 0x38-0x3f */
  c_1,c_1,c_1,c_1,c_1,c_1,c_1,c_1, /* 0x40-0x47 */
  c_1,c_1,c_1,c_1,c_1,c_1,c_1,c_1, /* 0x48-0x4f */
  c_1,c_1,c_1,c_1,c_1,c_1,c_1,c_1, /* 0x50-0x57 */
  c_1,c_1,c_1,c_1,c_1,c_1,c_1,c_1, /* 0x58-0x5f */
  c_1,c_1,c_EG,c_EG,c_1,c_1,c_op,c_ad, /* 0x60-0x67 */
  c_lv,c_EGlv,c_lb,c_EGlb,c_1,c_1,c_1,c_1, /* 0x68-0x6f */
  c_jxx,c_jxx,c_jxx,c_jxx,c_jxx,c_jxx,c_jxx,c_jxx, /* 0x70-0x77 */
  c_jxx,c_jxx,c_jxx,c_jxx,c_jxx,c_jxx,c_jxx,c_jxx, /* 0x78-0x7f */
  c_EGlb,c_EGlv,c_EGlb,c_EGlb,c_EG,c_EG,c_EG,c_EG, /* 0x80-0x87 */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG, /* 0x88-0x8f */
  c_1,c_1,c_1,c_1,c_1,c_1,c_1,c_1, /* 0x90-0x97 */
  c_1,c_1,c_callfar,c_1,c_1,c_1,c_1,c_1, /* 0x98-0x9f */
  c_O,c_O,c_O,c_O,c_1,c_1,c_1,c_1, /* 0xa0-0xa7 */
  c_lb,c_lv,c_1,c_1,c_1,c_1,c_1,c_1, /* 0xa8- 0xaf */
  c_2,c_2,c_2,c_2,c_2,c_2,c_2,c_2, /* 0xb0-0xb7 */
  c_lv,c_lv,c_lv,c_lv,c_lv,c_lv,c_lv,c_lv, /* 0xb8-0xbf */
  c_EGlb,c_EGlb,c_retnlw,c_retn,c_EG,c_EG,c_EGlb,c_EGlv, /* 0xc0-0xc7 */
  c_4,c_1,c_retflw,c_retf,c_int3,c_2,c_1,c_iret, /* 0xc8-0xcf */
  c_EG,c_EG,c_EG,c_EG,c_2,c_2,c_1,c_1, /* 0xd0-0xd7 */
  c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG,c_EG, /* 0xd8-0xdf */
  c_jxx,c_jxx,c_jxx,c_jxx,c_2,c_2,c_2,c_2, /* 0xe0-0xe7 */
  c_calljv,c_jmpnjv,c_jmpfap,c_jmpnjb,c_1,c_1,c_1,c_1, /* 0xe8-0xef */
  c_1,c_1,c_1,c_1, c_1,c_1,c_EGg3b,c_EGg3v, /* 0xf0-0xf7 */
  c_1,c_1,c_1,c_1,c_1,c_1,c_g4,c_g4 /* 0xf8-0xff */
};

#if ENABLE_DEBUG == 1

#define MAX_INSN_SAVE	20

static void
enter_save_insn (unsigned char *s, unsigned char b)
{
  int i;
  for (i=0;i<MAX_INSN_SAVE-1;i++)
    s[i]=s[i+1];
  s[MAX_INSN_SAVE-1]=b;
}

static void
print_save_insn (const char *name, unsigned char *s)
{
  int i;
  
  PRDEBUG("From %s: ",name);
  for (i=0;i<MAX_INSN_SAVE;i++)
  {
    PRDEBUG("%s0x%x",(i!=0 ? "," : ""), (unsigned int) s[i]);
  }
}
#endif

static size_t
getMemonic(int *aCode,uint32_t pc,volatile uint32_t *jmp_pc, __attribute__((unused)) const char *name, sImportname **ppimpname)
{
#if ENABLE_DEBUG == 1
  static unsigned char lw[MAX_INSN_SAVE];
#endif
  unsigned char *p;
  int addr_mode = 1;
  int oper_mode = 1;
  size_t sz = 0;
  unsigned char b;
  int tb1;

  for(;;) {
    p = (unsigned char *) map_va (pc + sz);
    if (!p) { *aCode=c_ill; return 0; }
    b = p[0];
    if (b==0x26 || b==0x2e || b==0x36 || b==0x3e || b==0x64 || b==0x65)
      ++sz;
    else if (b==0x66) { oper_mode^=1; sz++; }
    else if (b==0x67) { addr_mode^=1; sz++; }
    else if (b==0xf2 || b==0xf3 || b==0xf0) sz++;
    else break;
  }
  sz++;
  tb1=opMap1[(unsigned int) b];
  
redo_switch:
#if ENABLE_DEBUG == 1
  if (tb1!=c_ill) { enter_save_insn(lw,b); }
#endif
  switch (tb1) {
  case c_ill:
#if ENABLE_DEBUG == 1
    print_save_insn (name, lw);
    PRDEBUG(" 0x%x illegal ", (unsigned int) b);
#endif
    *aCode=c_ill; return 0;
  case c_4: sz++;/* fallthru */
  case c_3: sz++;/* fallthru */
  case c_lb:
  case c_2: sz++;/* fallthru */
  case c_retn: case c_retf:
  case c_iret: case c_int3:
  case c_ad: case c_op:
  case c_1: *aCode=tb1; return sz;
  case c_lv:
    if (oper_mode) sz+=4;
    else sz+=2;
    *aCode=tb1; return sz;
  case c_O: case c_calljv:
    if (addr_mode) sz+=4;
    else sz+=2;
    *aCode=tb1; return sz;
  case c_EG: case c_EGlv: case c_EGlb: case c_g4: case c_EGg3v: case c_EGg3b:
    p = (unsigned char *) map_va (pc + sz);
    sz++;
    if (!p) { *aCode=c_ill; return 0; }
    b = p[0];
#if ENABLE_DEBUG == 1
    enter_save_insn(lw,b);
#endif
    if (addr_mode) {
      if((b&0xc0)!=0xc0 && (b&0x7)==4)
        {
          p = (unsigned char *) map_va (pc + sz);
          if (!p) { *aCode=c_ill; return 0; }
#if ENABLE_DEBUG == 1
	  enter_save_insn(lw,p[0]);
#endif
          b&=~0x7; b|=(p[0]&7);
	  sz+=1;
	}
      if((b&0xc0)==0 && (b&7)==5)
        {
	  /* Here we check if for jmp instruction it points to an IAT entry.  */
	  if(tb1==c_g4 && ((b&0x38)==0x20 || (b&0x38)==0x28))
	    {
	      uint32_t vaddr;
	      sImportname *inss;
	      vaddr = *((uint32_t *) map_va (pc + sz));
	      inss = imp32_findbyaddress (vaddr);
	      if (inss)
		*ppimpname = inss;
	    }
	  sz+=4;
        }
      else if((b&0xc0)==0x40)
	sz+=1;
      else if((b&0xc0)==0x80)
	sz+=4;
    } else {
      if((b&0xc0)==0) {
	if((b&0x07)==6) sz+=2;
      } else if((b&0xc0)==0x40)
	sz+=1;
      else if((b&0xc0)==0x80)
	sz+=2;
    }
    if (tb1==c_EGlv) sz+=(oper_mode ? 4 : 2);
    else if(tb1==c_EGlb) sz++;
    else if(tb1==c_g4) {
      if ((b&0x38)==0x20 || (b&0x38)==0x28)
	tb1=c_int3;
      else if((b&0x38)==0x38)
        tb1=c_ill;
    } else if (tb1==c_EGg3v || tb1==c_EGg3b) {
      switch (((b&0x38)>>3)) {
      case 1:
      case 0: sz+= (tb1==c_EGg3v ? (oper_mode ? 4 : 2) : 1); break;
      default: break;
      }
    }
    *aCode=tb1; return sz;
  case c_jxx: case c_jmpnjb:
    p = (unsigned char *) map_va (pc + sz);
    if (!p) { *aCode=c_ill; return 0; }
    b = p[0];
    sz++;
    jmp_pc[0]=(uint32_t) pc + (uint32_t) sz;
    if ((b&0x80)!=0)
      jmp_pc[0] = jmp_pc[0] + (((uint32_t) b) | 0xffffff00);
    else
      jmp_pc[0] = jmp_pc[0] + (uint32_t) b;
    *aCode=tb1; return sz;
  case c_jmpnjv:
  case c_jxxv: 
    p = (unsigned char *) map_va (pc + sz);
    if (!p) { *aCode=c_ill; return 0; }
    if (oper_mode) { jmp_pc[0]=*((uint32_t *)p); sz+=4; }
    else {
      jmp_pc[0]=(uint32_t) *((uint16_t *)p);
      if ((jmp_pc[0]&0x8000)!=0) jmp_pc[0]|=0xffff0000;
      sz+=2;
    }
    jmp_pc[0]+=(uint32_t) pc+(uint32_t) sz;
#if ENABLE_DEBUG == 1
    if ((jmp_pc[0]&0xff000000)!=0) {
      print_save_insn (name, lw);
      PRDEBUG(" 0x%x illegal ", (unsigned int) b);
      PRDEBUG("jmp(cond) 0x%x (sz=%x,pc=%x,off=%x) ",
	      jmp_pc[0], (unsigned int) sz,(unsigned int) pc,
              (unsigned int) (jmp_pc[0]-(sz+pc)));
    }
#endif
    *aCode=(tb1==c_jxxv ? c_jxx : tb1);
    return sz;
  case c_0f:
    p = (unsigned char *) map_va (pc + sz);
    if (!p) { *aCode=c_ill; return 0; }
    b = p[0];
    sz++;
    tb1=opMap2[b];
    goto redo_switch;
  case c_jmpfap:
    sz+=4; if(oper_mode) sz+=2;
    *aCode=tb1; return sz;
  case c_callfar:
    sz+=4; if(oper_mode) sz+=2;
    *aCode=tb1; return sz;
  case c_retflw: case c_retnlw:
    p = (unsigned char *) map_va (pc + sz);
    if (!p) { *aCode=c_ill; return 0; }
    jmp_pc[0]=*((uint16_t*) p);
    sz+=2;
    *aCode=tb1;
#if ENABLE_DEBUG == 1
    if (jmp_pc[0]>0x100 || jmp_pc[0]&3) {
      print_save_insn (name, lw);
      PRDEBUG(" 0x%x illegal ", (unsigned int) b);
      PRDEBUG("ret dw 0x%x (sz=%x) ", (unsigned int) jmp_pc[0], (unsigned int) sz);
    }
#endif
    return sz;
  default:
    PRDEBUG(" * opcode 0x%x (tbl=%d) unknown\n", (unsigned int) b, tb1);
    sz=0; *aCode=c_ill; break;
  }
  return sz;
}

static void
decode_mangle (FILE *fp, const char *n)
{
#ifdef HAVE_LIBMANGLE
  libmangle_gc_context_t *gc = libmangle_generate_gc ();
  libmangle_tokens_t ptok;
#endif
  if (!fp || !n || *n == 0)
    return;
#ifdef HAVE_LIBMANGLE
  ptok = libmangle_decode_ms_name (gc, n);
  if (ptok)
    {
      char *h = libmangle_sprint_decl (ptok);
      if (h)
	{
	  fprintf (fp, "; %s\n", h);
	  free (h);
	}
    }
  libmangle_release_gc (gc);
#endif
}
