//========================================================================
//
// pdfinfo.cc
//
// Copyright 1998-2003 Glyph & Cog, LLC
// Copyright 2013 Igalia S.L.
//
//========================================================================

//========================================================================
//
// Modified under the Poppler project - http://poppler.freedesktop.org
//
// All changes made under the Poppler project to this file are licensed
// under GPL version 2 or later
//
// Copyright (C) 2006 Dom Lachowicz <cinamod@hotmail.com>
// Copyright (C) 2007-2010, 2012, 2016-2018 Albert Astals Cid <aacid@kde.org>
// Copyright (C) 2010 Hib Eris <hib@hiberis.nl>
// Copyright (C) 2011 Vittal Aithal <vittal.aithal@cognidox.com>
// Copyright (C) 2012, 2013, 2016-2018 Adrian Johnson <ajohnson@redneon.com>
// Copyright (C) 2012 Fabio D'Urso <fabiodurso@hotmail.it>
// Copyright (C) 2013 Adrian Perez de Castro <aperez@igalia.com>
// Copyright (C) 2013 Suzuki Toshiya <mpsuzuki@hiroshima-u.ac.jp>
// Copyright (C) 2018 Klarälvdalens Datakonsult AB, a KDAB Group company, <info@kdab.com>. Work sponsored by the LiMux project of the city of Munich
// Copyright (C) 2018 Adam Reichold <adam.reichold@t-online.de>
// Copyright (C) 2018 Evangelos Rigas <erigas@rnd2.org>
// Copyright (C) 2019 Christian Persch <chpe@src.gnome.org>
//
// To see a description of the changes please see the Changelog file that
// came with your tarball or type make ChangeLog if you are building from git
//
//========================================================================

#include "config.h"
#include <poppler-config.h>
#include <stdio.h>
#include <stdlib.h>
#include <stddef.h>
#include <string.h>
#include <time.h>
#include <math.h>
#include <map>
#include "parseargs.h"
#include "printencodings.h"
#include "goo/GooString.h"
#include "goo/gfile.h"
#include "goo/glibc.h"
#include "goo/gmem.h"
#include "GlobalParams.h"
#include "Object.h"
#include "Stream.h"
#include "Array.h"
#include "Dict.h"
#include "XRef.h"
#include "Catalog.h"
#include "Page.h"
#include "PDFDoc.h"
#include "PDFDocFactory.h"
#include "CharTypes.h"
#include "UnicodeMap.h"
#include "UTF.h"
#include "Error.h"
#include "DateInfo.h"
#include "JSInfo.h"
#include "StructTreeRoot.h"
#include "StructElement.h"
#include "Win32Console.h"


static int firstPage = 1;
static int lastPage = 0;
static bool printBoxes = false;
static bool printMetadata = false;
static bool printJS = false;
static bool isoDates = false;
static bool rawDates = false;
static char textEncName[128] = "";
static char ownerPassword[33] = "\001";
static char userPassword[33] = "\001";
static bool printVersion = false;
static bool printHelp = false;
static bool printEnc = false;
static bool printStructure = false;
static bool printStructureText = false;
static bool printDests = false;

static const ArgDesc argDesc[] = {
  {"-f",      argInt,      &firstPage,        0,
   "first page to convert"},
  {"-l",      argInt,      &lastPage,         0,
   "last page to convert"},
  {"-box",    argFlag,     &printBoxes,       0,
   "print the page bounding boxes"},
  {"-meta",   argFlag,     &printMetadata,    0,
   "print the document metadata (XML)"},
  {"-js",     argFlag,     &printJS,          0,
   "print all JavaScript in the PDF"},
  {"-struct", argFlag,     &printStructure,   0,
   "print the logical document structure (for tagged files)"},
  {"-struct-text", argFlag, &printStructureText, 0,
   "print text contents along with document structure (for tagged files)"},
  {"-isodates", argFlag,   &isoDates,         0,
   "print the dates in ISO-8601 format"},
  {"-rawdates", argFlag,   &rawDates,         0,
   "print the undecoded date strings directly from the PDF file"},
  {"-dests",     argFlag,  &printDests,       0,
   "print all named destinations in the PDF"},
  {"-enc",    argString,   textEncName,    sizeof(textEncName),
   "output text encoding name"},
  {"-listenc",argFlag,     &printEnc,      0,
   "list available encodings"},
  {"-opw",    argString,   ownerPassword,  sizeof(ownerPassword),
   "owner password (for encrypted files)"},
  {"-upw",    argString,   userPassword,   sizeof(userPassword),
   "user password (for encrypted files)"},
  {"-v",      argFlag,     &printVersion,  0,
   "print copyright and version info"},
  {"-h",      argFlag,     &printHelp,     0,
   "print usage information"},
  {"-help",   argFlag,     &printHelp,     0,
   "print usage information"},
  {"--help",  argFlag,     &printHelp,     0,
   "print usage information"},
  {"-?",      argFlag,     &printHelp,     0,
   "print usage information"},
  {}
};

static void printInfoString(Dict *infoDict, const char *key, const char *text,
			    UnicodeMap *uMap) {
  const GooString *s1;
  Unicode *u;
  char buf[8];
  int i, n, len;

  Object obj = infoDict->lookup(key);
  if (obj.isString()) {
    fputs(text, stdout);
    s1 = obj.getString();
    len = TextStringToUCS4(s1, &u);
    for (i = 0; i < len; i++) {
      n = uMap->mapUnicode(u[i], buf, sizeof(buf));
      fwrite(buf, 1, n, stdout);
    }
    gfree(u);
    fputc('\n', stdout);
  }
}

static void printInfoDate(Dict *infoDict, const char *key, const char *text) {
  const char *s;
  int year, mon, day, hour, min, sec, tz_hour, tz_minute;
  char tz;
  struct tm tmStruct;
  time_t time;
  char buf[256];

  Object obj = infoDict->lookup(key);
  if (obj.isString()) {
    fputs(text, stdout);
    s = obj.getString()->c_str();
    // TODO do something with the timezone info
    if ( parseDateString( s, &year, &mon, &day, &hour, &min, &sec, &tz, &tz_hour, &tz_minute ) ) {
      tmStruct.tm_year = year - 1900;
      tmStruct.tm_mon = mon - 1;
      tmStruct.tm_mday = day;
      tmStruct.tm_hour = hour;
      tmStruct.tm_min = min;
      tmStruct.tm_sec = sec;
      tmStruct.tm_wday = -1;
      tmStruct.tm_yday = -1;
      tmStruct.tm_isdst = -1;
      // compute the tm_wday and tm_yday fields
      time = timegm(&tmStruct);
      if (time != (time_t)-1) {
	int offset = (tz_hour*60 + tz_minute)*60;
	if (tz == '-')
	  offset *= -1;
	time -= offset;
	localtime_r(&time, &tmStruct);
	strftime(buf, sizeof(buf), "%c %Z", &tmStruct);
	fputs(buf, stdout);
      } else {
	fputs(s, stdout);
      }
    } else {
      fputs(s, stdout);
    }
    fputc('\n', stdout);
  }
}

static void printISODate(Dict *infoDict, const char *key, const char *text)
{
  const char *s;
  int year, mon, day, hour, min, sec, tz_hour, tz_minute;
  char tz;

  Object obj = infoDict->lookup(key);
  if (obj.isString()) {
    fputs(text, stdout);
    s = obj.getString()->c_str();
    if ( parseDateString( s, &year, &mon, &day, &hour, &min, &sec, &tz, &tz_hour, &tz_minute ) ) {
      fprintf(stdout, "%04d-%02d-%02dT%02d:%02d:%02d", year, mon, day, hour, min, sec);
      if (tz_hour == 0 && tz_minute == 0) {
	fprintf(stdout, "Z");
      } else {
	fprintf(stdout, "%c%02d", tz, tz_hour);
	if (tz_minute)
	  fprintf(stdout, ":%02d", tz_minute);
      }
    } else {
      fputs(s, stdout);
    }
    fputc('\n', stdout);
  }
}

static void printBox(const char *text, const PDFRectangle *box) {
  printf("%s%8.2f %8.2f %8.2f %8.2f\n",
	 text, box->x1, box->y1, box->x2, box->y2);
}

static void printIndent(unsigned indent) {
  while (indent--) {
    putchar(' ');
    putchar(' ');
  }
}

static void printAttribute(const Attribute *attribute, unsigned indent)
{
  printIndent(indent);
  printf(" /%s ", attribute->getTypeName());
  if (attribute->getType() == Attribute::UserProperty) {
    GooString *name = attribute->getName();
    printf("(%s) ", name->c_str());
    delete name;
  }
  attribute->getValue()->print(stdout);
  if (attribute->getFormattedValue()) {
    printf(" \"%s\"", attribute->getFormattedValue());
  }
  if (attribute->isHidden()) {
    printf(" [hidden]");
  }
}

static void printStruct(const StructElement *element, unsigned indent) {
  if (element->isObjectRef()) {
    printIndent(indent);
    printf("Object %i %i\n", element->getObjectRef().num, element->getObjectRef().gen);
    return;
  }

  if (printStructureText && element->isContent()) {
    GooString *text = element->getText(false);
    printIndent(indent);
    if (text) {
      printf("\"%s\"\n", text->c_str());
    } else {
      printf("(No content?)\n");
    }
    delete text;
  }

  if (!element->isContent()) {
      printIndent(indent);
      printf("%s", element->getTypeName());
      if (element->getID()) {
          printf(" <%s>", element->getID()->c_str());
      }
      if (element->getTitle()) {
          printf(" \"%s\"", element->getTitle()->c_str());
      }
      if (element->getRevision() > 0) {
          printf(" r%u", element->getRevision());
      }
      if (element->isInline() || element->isBlock()) {
          printf(" (%s)", element->isInline() ? "inline" : "block");
      }
      if (element->getNumAttributes()) {
          putchar(':');
          for (unsigned i = 0; i < element->getNumAttributes(); i++) {
              putchar('\n');
              printAttribute(element->getAttribute(i), indent + 1);
          }
      }

      putchar('\n');
      for (unsigned i = 0; i < element->getNumChildren(); i++) {
          printStruct(element->getChild(i), indent + 1);
      }
  }
}

struct GooStringCompare {
  bool operator() (GooString* lhs, GooString* rhs) const {
    return lhs->cmp(const_cast<GooString*>(rhs)) < 0;
  }
};

static void printLinkDest(LinkDest *dest) {
  GooString s;

  switch (dest->getKind()) {
    case destXYZ:
      s.append("[ XYZ ");
      if (dest->getChangeLeft()) {
	s.appendf("{0:4.0g} ", dest->getLeft());
      } else {
	s.append("null ");
      }
      if (dest->getChangeTop()) {
	s.appendf("{0:4.0g} ", dest->getTop());
      } else {
	s.append("null ");
      }
      if (dest->getChangeZoom()) {
	s.appendf("{0:4.2f} ", dest->getZoom());
      } else {
	s.append("null ");
      }
      break;
    case destFit:
      s.append("[ Fit ");
      break;
    case destFitH:
      if (dest->getChangeTop()) {
	s.appendf("[ FitH {0:4.0g} ", dest->getTop());
      } else {
	s.append("[ FitH null ");
      }
      break;
    case destFitV:
      if (dest->getChangeLeft()) {
	s.appendf("[ FitV {0:4.0g} ", dest->getLeft());
      } else {
	s.append("[ FitV null ");
      }
      break;
    case destFitR:
      s.appendf("[ FitR {0:4.0g} {1:4.0g} {2:4.0g} {3:4.0g} ",
	      dest->getLeft(),
	      dest->getBottom(),
	      dest->getRight(),
	      dest->getTop());
      break;
    case destFitB:
      s.append("[ FitB ");
      break;
    case destFitBH:
      if (dest->getChangeTop()) {
	s.appendf("[ FitBH {0:4.0g} ", dest->getTop());
      } else {
	s.append("[ FitBH null ");
      }
      break;
    case destFitBV:
      if (dest->getChangeLeft()) {
	s.appendf("[ FitBV {0:4.0g} ", dest->getLeft());
      } else {
	s.append("[ FitBV null ");
      }
      break;
  }

  s.append("                                ");
  s.setChar(26, ']');
  s.setChar(27, '\0');
  printf("%s", s.c_str());
}

static void printDestinations(PDFDoc *doc, UnicodeMap *uMap) {
  std::map<Ref,std::map<GooString*,LinkDest*,GooStringCompare> > map;

  int numDests = doc->getCatalog()->numDestNameTree();
  for (int i = 0; i < numDests; i++) {
    GooString *name = new GooString(doc->getCatalog()->getDestNameTreeName(i));
    LinkDest *dest = doc->getCatalog()->getDestNameTreeDest(i);
    if (dest && dest->isPageRef()) {
      map[dest->getPageRef()].insert(std::make_pair(name, dest));
    } else {
      delete name;
      delete dest;
    }
  }

  numDests = doc->getCatalog()->numDests();
  for (int i = 0; i < numDests; i++) {
    GooString *name = new GooString(doc->getCatalog()->getDestsName(i));
    LinkDest *dest = doc->getCatalog()->getDestsDest(i);
    if (dest && dest->isPageRef()) {
      map[dest->getPageRef()].insert(std::make_pair(name, dest));
    } else {
      delete name;
      delete dest;
    }
  }

  printf("Page  Destination                 Name\n");
  for (int i = firstPage; i <= lastPage; i++) {
    Ref *ref = doc->getCatalog()->getPageRef(i);
    if (ref) {
      auto pageDests = map.find(*ref);
      if (pageDests != map.end()) {
	for (auto& it: pageDests->second) {
	  printf("%4d ", i);
	  printLinkDest(it.second);
	  printf(" \"");
	  Unicode *u;
	  char buf[8];
	  const int len = TextStringToUCS4(it.first, &u);
	  for (int j = 0; j < len; j++) {
	    const int n = uMap->mapUnicode(u[j], buf, sizeof(buf));
	    fwrite(buf, 1, n, stdout);
	  }
	  gfree(u);
	  printf("\"\n");
	  delete it.first;
	  delete it.second;
	}
      }
    }
  }
}

static void printPdfSubtype(PDFDoc *doc, UnicodeMap *uMap) {
  const Object info = doc->getDocInfo();
  if (info.isDict()) {
    const PDFSubtype pdftype = doc->getPDFSubtype();

    if ((pdftype == subtypeNull) | (pdftype == subtypeNone)) {
      return;
    }

    std::unique_ptr<GooString> part;
    std::unique_ptr<GooString> abbr;
    std::unique_ptr<GooString> standard;
    std::unique_ptr<GooString> typeExp;
    std::unique_ptr<GooString> confExp;

    // Form title from PDFSubtype
    switch (pdftype)
    {
      case subtypePDFA:
        printInfoString(info.getDict(), "GTS_PDFA1Version", "PDF subtype:    ", uMap);
        typeExp.reset( new GooString("ISO 19005 - Electronic document file format for long-term preservation (PDF/A)") );
        standard.reset(  new GooString("ISO 19005") );
        abbr.reset( new GooString("PDF/A") );
        break;
      case subtypePDFE:
        printInfoString(info.getDict(), "GTS_PDFEVersion", "PDF subtype:    ", uMap);
        typeExp.reset( new GooString("ISO 24517 - Engineering document format using PDF (PDF/E)") );
        standard.reset( new GooString("ISO 24517") );
        abbr.reset( new GooString("PDF/E") );
        break;
      case subtypePDFUA:
        printInfoString(info.getDict(), "GTS_PDFUAVersion", "PDF subtype:    ", uMap);
        typeExp.reset( new GooString("ISO 14289 - Electronic document file format enhancement for accessibility (PDF/UA)") );
        standard.reset( new GooString("ISO 14289") );
        abbr.reset( new GooString("PDF/UA") );
        break;
      case subtypePDFVT:
        printInfoString(info.getDict(), "GTS_PDFVTVersion", "PDF subtype:    ", uMap);
        typeExp.reset( new GooString("ISO 16612 - Electronic document file format for variable data exchange (PDF/VT)") );
        standard.reset( new GooString("ISO 16612") );
        abbr.reset( new GooString("PDF/VT") );
        break;
      case subtypePDFX:
        printInfoString(info.getDict(), "GTS_PDFXVersion", "PDF subtype:    ", uMap);
        typeExp.reset( new GooString("ISO 15930 - Electronic document file format for prepress digital data exchange (PDF/X)") );
        standard.reset( new GooString("ISO 15930") );
        abbr.reset( new GooString("PDF/X") );
        break;
      case subtypeNone:
      case subtypeNull:
      default:
        return;
    }

    // Form the abbreviation from PDFSubtypePart and PDFSubtype
    const PDFSubtypePart subpart = doc->getPDFSubtypePart();
    switch (pdftype) {
      case subtypePDFX:
        switch (subpart) {
          case subtypePart1:
            abbr->append("-1:2001");
            break;
          case subtypePart2:
            abbr->append("-2");
            break;
          case subtypePart3:
            abbr->append("-3:2002");
            break;
          case subtypePart4:
            abbr->append("-1:2003");
            break;
          case subtypePart5:
            abbr->append("-2");
            break;
          case subtypePart6:
            abbr->append("-3:2003");
            break;
          case subtypePart7:
            abbr->append("-4");
            break;
          case subtypePart8:
            abbr->append("-5");
            break;
          default:
            break;
        }
        break;
      case subtypeNone:
      case subtypeNull:
        break;
      default:
        abbr->appendf("-{0:d}", subpart);
        break;
    }

    // Form standard from PDFSubtypePart
    switch (subpart) {
      case subtypePartNone:
      case subtypePartNull:
        break;
      default:
        standard->appendf("-{0:d}", subpart);
        break;
    }

    // Form the subtitle from PDFSubtypePart and PDFSubtype
    switch (pdftype) {
      case subtypePDFA:
          switch (subpart) {
          case subtypePart1:
            part.reset( new GooString("Use of PDF 1.4") );
            break;
          case subtypePart2:
            part.reset( new GooString("Use of ISO 32000-1") );
            break;
          case subtypePart3:
            part.reset( new GooString("Use of ISO 32000-1 with support for embedded files") );
            break;
          default:
            break;
          }
          break;
      case subtypePDFE:
        switch (subpart) {
          case subtypePart1:
            part.reset( new GooString("Use of PDF 1.6") );
            break;
          default:
            break;
          }
          break;
      case subtypePDFUA:
        switch (subpart) {
          case subtypePart1:
            part.reset( new GooString("Use of ISO 32000-1") );
            break;
          case subtypePart2:
            part.reset( new GooString("Use of ISO 32000-2") );
            break;
          case subtypePart3:
            part.reset( new GooString("Use of ISO 32000-1 with support for embedded files") );
            break;
          default:
            break;
          }
          break;
      case subtypePDFVT:
        switch (subpart) {
          case subtypePart1:
            part.reset( new GooString("Using PPML 2.1 and PDF 1.4") );
            break;
          case subtypePart2:
            part.reset( new GooString("Using PDF/X-4 and PDF/X-5 (PDF/VT-1 and PDF/VT-2)") );
            break;
          case subtypePart3:
            part.reset( new GooString("Using PDF/X-6 (PDF/VT-3)") );
            break;
          default:
            break;
          }
          break;
      case subtypePDFX:
        switch (subpart) {
          case subtypePart1:
            part.reset( new GooString("Complete exchange using CMYK data (PDF/X-1 and PDF/X-1a)") );
            break;
          case subtypePart3:
            part.reset( new GooString("Complete exchange suitable for colour-managed workflows (PDF/X-3)") );
            break;
          case subtypePart4:
            part.reset( new GooString("Complete exchange of CMYK and spot colour printing data using PDF 1.4 (PDF/X-1a)") );
            break;
          case subtypePart5:
            part.reset( new GooString("Partial exchange of printing data using PDF 1.4 (PDF/X-2) [Withdrawn]") );
            break;
          case subtypePart6:
            part.reset( new GooString("Complete exchange of printing data suitable for colour-managed workflows using PDF 1.4 (PDF/X-3)") );
            break;
          case subtypePart7:
            part.reset( new GooString("Complete exchange of printing data (PDF/X-4) and partial exchange of printing data with external profile reference (PDF/X-4p) using PDF 1.6") );
            break;
          case subtypePart8:
            part.reset( new GooString("Partial exchange of printing data using PDF 1.6 (PDF/X-5)") );
            break;
          default:
            break;
          }
          break;
      default:
        break;
    }

    // Form Conformance explanation from PDFSubtypeConformance
    switch (doc->getPDFSubtypeConformance())
    {
      case subtypeConfA:
        confExp.reset( new GooString("Level A, Accessible") );
        break;
      case subtypeConfB:
        confExp.reset( new GooString("Level B, Basic") );
        break;
      case subtypeConfG:
        confExp.reset( new GooString("Level G, External graphical content") );
        break;
      case subtypeConfN:
        confExp.reset( new GooString("Level N, External ICC profile") );
        break;
      case subtypeConfP:
        confExp.reset( new GooString("Level P, Embedded ICC profile") );
        break;
      case subtypeConfPG:
        confExp.reset( new GooString("Level PG, Embedded ICC profile and external graphical content") );
        break;
      case subtypeConfU:
        confExp.reset( new GooString("Level U, Unicode support") );
        break;
      case subtypeConfNone:
      case subtypeConfNull:
      default:
        confExp.reset();
        break;
    }

    printf("    Title:         %s\n",typeExp->c_str());
    printf("    Abbreviation:  %s\n", abbr->c_str());
    if (part.get())
      printf("    Subtitle:      Part %d: %s\n", subpart, part->c_str());
    else
      printf("    Subtitle:      Part %d\n", subpart);
    printf("    Standard:      %s-%d\n", typeExp->toStr().substr(0,9).c_str(), subpart);
    if (confExp.get())
      printf("    Conformance:   %s\n", confExp->c_str());
  }
}

static void printInfo(PDFDoc *doc, UnicodeMap *uMap, long long filesize, bool multiPage) {
  Page *page;
  char buf[256];
  double w, h, wISO, hISO;
  int pg, i;
  int r;

  // print doc info
  Object info = doc->getDocInfo();
  if (info.isDict()) {
    printInfoString(info.getDict(), "Title",        "Title:          ", uMap);
    printInfoString(info.getDict(), "Subject",      "Subject:        ", uMap);
    printInfoString(info.getDict(), "Keywords",     "Keywords:       ", uMap);
    printInfoString(info.getDict(), "Author",       "Author:         ", uMap);
    printInfoString(info.getDict(), "Creator",      "Creator:        ", uMap);
    printInfoString(info.getDict(), "Producer",     "Producer:       ", uMap);
    if (isoDates) {
      printISODate(info.getDict(),   "CreationDate", "CreationDate:   ");
      printISODate(info.getDict(),   "ModDate",      "ModDate:        ");
    } else if (rawDates) {
      printInfoString(info.getDict(), "CreationDate", "CreationDate:   ",
		      uMap);
      printInfoString(info.getDict(), "ModDate",      "ModDate:        ",
		      uMap);
    } else {
      printInfoDate(info.getDict(),   "CreationDate", "CreationDate:   ");
      printInfoDate(info.getDict(),   "ModDate",      "ModDate:        ");
    }
  }

  // print tagging info
   printf("Tagged:         %s\n",
	  (doc->getCatalog()->getMarkInfo() & Catalog::markInfoMarked) ? "yes" : "no");
   printf("UserProperties: %s\n",
	  (doc->getCatalog()->getMarkInfo() & Catalog::markInfoUserProperties) ? "yes" : "no");
   printf("Suspects:       %s\n",
	  (doc->getCatalog()->getMarkInfo() & Catalog::markInfoSuspects) ? "yes" : "no");

  // print form info
  switch (doc->getCatalog()->getFormType())
  {
    case Catalog::NoForm:
      printf("Form:           none\n");
      break;
    case Catalog::AcroForm:
      printf("Form:           AcroForm\n");
      break;
    case Catalog::XfaForm:
      printf("Form:           XFA\n");
      break;
  }

  // print javascript info
  {
    JSInfo jsInfo(doc, firstPage - 1);
    jsInfo.scanJS(lastPage - firstPage + 1);
    printf("JavaScript:     %s\n", jsInfo.containsJS() ? "yes" : "no");
  }

  // print page count
  printf("Pages:          %d\n", doc->getNumPages());

  // print encryption info
  printf("Encrypted:      ");
  if (doc->isEncrypted()) {
    unsigned char *fileKey;
    CryptAlgorithm encAlgorithm;
    int keyLength;
    doc->getXRef()->getEncryptionParameters(&fileKey, &encAlgorithm, &keyLength);

    const char *encAlgorithmName = "unknown";
    switch (encAlgorithm)
    {
      case cryptRC4:
	encAlgorithmName = "RC4";
	break;
      case cryptAES:
	encAlgorithmName = "AES";
	break;
      case cryptAES256:
	encAlgorithmName = "AES-256";
	break;
      case cryptNone:
	break;
    }

    printf("yes (print:%s copy:%s change:%s addNotes:%s algorithm:%s)\n",
	   doc->okToPrint(true) ? "yes" : "no",
	   doc->okToCopy(true) ? "yes" : "no",
	   doc->okToChange(true) ? "yes" : "no",
	   doc->okToAddNotes(true) ? "yes" : "no",
	   encAlgorithmName);
  } else {
    printf("no\n");
  }

  // print page size
  for (pg = firstPage; pg <= lastPage; ++pg) {
    w = doc->getPageCropWidth(pg);
    h = doc->getPageCropHeight(pg);
    if (multiPage) {
      printf("Page %4d size: %g x %g pts", pg, w, h);
    } else {
      printf("Page size:      %g x %g pts", w, h);
    }
    if ((fabs(w - 612) < 0.1 && fabs(h - 792) < 0.1) ||
	(fabs(w - 792) < 0.1 && fabs(h - 612) < 0.1)) {
      printf(" (letter)");
    } else {
      hISO = sqrt(sqrt(2.0)) * 7200 / 2.54;
      wISO = hISO / sqrt(2.0);
      for (i = 0; i <= 6; ++i) {
	if ((fabs(w - wISO) < 1 && fabs(h - hISO) < 1) ||
	    (fabs(w - hISO) < 1 && fabs(h - wISO) < 1)) {
	  printf(" (A%d)", i);
	  break;
	}
	hISO = wISO;
	wISO /= sqrt(2.0);
      }
    }
    printf("\n");
    r = doc->getPageRotate(pg);
    if (multiPage) {
      printf("Page %4d rot:  %d\n", pg, r);
    } else {
      printf("Page rot:       %d\n", r);
    }
  }

  // print the boxes
  if (printBoxes) {
    if (multiPage) {
      for (pg = firstPage; pg <= lastPage; ++pg) {
	page = doc->getPage(pg);
	if (!page) {
          error(errSyntaxError, -1, "Failed to print boxes for page {0:d}", pg);
	  continue;
	}
	sprintf(buf, "Page %4d MediaBox: ", pg);
	printBox(buf, page->getMediaBox());
	sprintf(buf, "Page %4d CropBox:  ", pg);
	printBox(buf, page->getCropBox());
	sprintf(buf, "Page %4d BleedBox: ", pg);
	printBox(buf, page->getBleedBox());
	sprintf(buf, "Page %4d TrimBox:  ", pg);
	printBox(buf, page->getTrimBox());
	sprintf(buf, "Page %4d ArtBox:   ", pg);
	printBox(buf, page->getArtBox());
      }
    } else {
      page = doc->getPage(firstPage);
      if (!page) {
        error(errSyntaxError, -1, "Failed to print boxes for page {0:d}", firstPage);
      } else {
        printBox("MediaBox:       ", page->getMediaBox());
        printBox("CropBox:        ", page->getCropBox());
        printBox("BleedBox:       ", page->getBleedBox());
        printBox("TrimBox:        ", page->getTrimBox());
        printBox("ArtBox:         ", page->getArtBox());
      }
    }
  }

  // print file size
  printf("File size:      %lld bytes\n", filesize);

  // print linearization info
  printf("Optimized:      %s\n", doc->isLinearized() ? "yes" : "no");

  // print PDF version
  printf("PDF version:    %d.%d\n", doc->getPDFMajorVersion(), doc->getPDFMinorVersion());

  printPdfSubtype(doc, uMap);
}

int main(int argc, char *argv[]) {
  PDFDoc *doc;
  GooString *fileName;
  GooString *ownerPW, *userPW;
  UnicodeMap *uMap;
  FILE *f;
  bool ok;
  int exitCode;
  bool multiPage;

  exitCode = 99;

  // parse args
  Win32Console win32console(&argc, &argv);
  ok = parseArgs(argDesc, &argc, argv);
  if (!ok || (argc != 2 && !printEnc) || printVersion || printHelp) {
    fprintf(stderr, "pdfinfo version %s\n", PACKAGE_VERSION);
    fprintf(stderr, "%s\n", popplerCopyright);
    fprintf(stderr, "%s\n", xpdfCopyright);
    if (!printVersion) {
      printUsage("pdfinfo", "<PDF-file>", argDesc);
    }
    if (printVersion || printHelp)
      exitCode = 0;
    goto err0;
  }

  if (printStructureText)
    printStructure = true;

  // read config file
  globalParams = new GlobalParams();

  if (printEnc) {
    printEncodings();
    delete globalParams;
    exitCode = 0;
    goto err0;
  }

  fileName = new GooString(argv[1]);

  if (textEncName[0]) {
    globalParams->setTextEncoding(textEncName);
  }

  // get mapping to output encoding
  if (!(uMap = globalParams->getTextEncoding())) {
    error(errCommandLine, -1, "Couldn't get text encoding");
    delete fileName;
    goto err1;
  }

  // open PDF file
  if (ownerPassword[0] != '\001') {
    ownerPW = new GooString(ownerPassword);
  } else {
    ownerPW = nullptr;
  }
  if (userPassword[0] != '\001') {
    userPW = new GooString(userPassword);
  } else {
    userPW = nullptr;
  }

  if (fileName->cmp("-") == 0) {
      delete fileName;
      fileName = new GooString("fd://0");
  }

  doc = PDFDocFactory().createPDFDoc(*fileName, ownerPW, userPW);

  if (userPW) {
    delete userPW;
  }
  if (ownerPW) {
    delete ownerPW;
  }
  if (!doc->isOk()) {
    exitCode = 1;
    goto err2;
  }

  // get page range
  if (firstPage < 1) {
    firstPage = 1;
  }
  if (lastPage == 0) {
    multiPage = false;
  } else {
    multiPage = true;
  }
  if (lastPage < 1 || lastPage > doc->getNumPages()) {
    lastPage = doc->getNumPages();
  }
  if (lastPage < firstPage) {
    error(errCommandLine, -1,
          "Wrong page range given: the first page ({0:d}) can not be after the last page ({1:d}).",
          firstPage, lastPage);
    goto err2;
  }

  if (printMetadata) {
    // print the metadata
    const GooString *metadata = doc->readMetadata();
    if (metadata) {
      fputs(metadata->c_str(), stdout);
      fputc('\n', stdout);
      delete metadata;
    }
  } else if (printJS) {
    // print javascript
    JSInfo jsInfo(doc, firstPage - 1);
    jsInfo.scanJS(lastPage - firstPage + 1, stdout, uMap);
  } else if (printStructure || printStructureText) {
    // print structure
    const StructTreeRoot *structTree = doc->getCatalog()->getStructTreeRoot();
    if (structTree) {
      for (unsigned i = 0; i < structTree->getNumChildren(); i++) {
	printStruct(structTree->getChild(i), 0);
      }
    }
  } else if (printDests) {
    printDestinations(doc, uMap);
  } else {
    // print info
    long long filesize = 0;

    f = fopen(fileName->c_str(), "rb");
    if (f) {
      Gfseek(f, 0, SEEK_END);
      filesize = Gftell(f);
      fclose(f);
    }

    if (multiPage == false)
      lastPage = 1;

    printInfo(doc, uMap, filesize, multiPage);
  }
  exitCode = 0;

  // clean up
 err2:
  uMap->decRefCnt();
  delete doc;
  delete fileName;
 err1:
  delete globalParams;
 err0:

  return exitCode;
}
