/* This file was generated by configgen on Sun Aug 13 14:05:26 2000
 * from config_templ.l
 *
 * DO NOT EDIT!
 */

/******************************************************************************
 *
 * $Id: config_templ.l,v 1.5 2000/08/05 18:36:35 root Exp $
 *
 * Copyright (C) 1997-2000 by Dimitri van Heesch.
 *
 * Permission to use, copy, modify, and distribute this software and its
 * documentation under the terms of the GNU General Public License is hereby 
 * granted. No representations are made about the suitability of this software 
 * for any purpose. It is provided "as is" without express or implied warranty.
 * See the GNU General Public License for more details.
 *
 */

%{

/*
 *	includes
 */
#include <stdio.h>
#include <stdlib.h>
#include <iostream.h>
#include <assert.h>
#include <ctype.h>

#include <qfileinfo.h>
#include <qdir.h>
#include <qtextstream.h>
#include <qregexp.h>
#include <qstack.h>
  
#include "config.h"
#include "version.h"
  
#ifdef DOXYWIZARD  
#include <stdarg.h>
void err(const char *fmt, ...)
{
  va_list args;
  va_start(args, fmt);
  vfprintf(stderr, fmt, args);
  va_end(args); 
}
void warn_cont(const char *fmt, ...)
{
  va_list args;
  va_start(args, fmt);
  vfprintf(stderr, fmt, args);
  va_end(args);
}
void initWarningFormat()
{
}
#else
#include "doxygen.h"
#include "message.h"
#include "pre.h"
#include "version.h"
#include "language.h"
#endif

#define MAX_INCLUDE_DEPTH 10
#define YY_NEVER_INTERACTIVE 1
#define YY_NO_UNPUT
  
/* -----------------------------------------------------------------
 *
 *	exported variables
 */
  
QCString Config::projectName;
QCString Config::projectNumber;
QCString Config::outputDir;
QCString Config::outputLanguage = "English";
bool     Config::extractAllFlag = FALSE;
bool     Config::extractPrivateFlag = FALSE;
bool     Config::extractStaticFlag = FALSE;
bool     Config::hideMemberFlag = FALSE;
bool     Config::hideClassFlag = FALSE;
bool     Config::briefMemDescFlag = TRUE;
bool     Config::repeatBriefFlag = TRUE;
bool     Config::alwaysDetailsFlag = FALSE;
bool     Config::fullPathNameFlag = FALSE;
QStrList Config::stripFromPath;
bool     Config::internalDocsFlag = FALSE;
bool     Config::classDiagramFlag = TRUE;
bool     Config::sourceBrowseFlag = FALSE;
bool     Config::inlineSourceFlag = FALSE;
bool     Config::stripCommentsFlag = TRUE;
bool     Config::caseSensitiveNames = TRUE;
bool     Config::hideScopeNames = FALSE;
bool     Config::verbatimHeaderFlag = TRUE;
bool     Config::showIncFileFlag = TRUE;
bool     Config::autoBriefFlag = TRUE;
bool     Config::inheritDocsFlag = TRUE;
bool     Config::inlineInfoFlag = TRUE;
bool     Config::sortMembersFlag = TRUE;
int      Config::tabSize = 8;
QStrList Config::sectionFilterList;
bool     Config::generateTodoList = TRUE;
bool     Config::generateTestList = TRUE;
bool     Config::quietFlag = FALSE;
bool     Config::warningFlag = TRUE;
bool     Config::warningUndocFlag = TRUE;
QCString Config::warnFormat = "$file:$line: $text";
QStrList Config::inputSources;
QStrList Config::filePatternList;
bool     Config::recursiveFlag = FALSE;
QStrList Config::excludeSources;
QStrList Config::excludePatternList;
QStrList Config::examplePath;
QStrList Config::examplePatternList;
QStrList Config::imagePath;
QCString Config::inputFilter;
bool     Config::alphaIndexFlag = FALSE;
int      Config::colsInAlphaIndex = 5;
QStrList Config::ignorePrefixList;
bool     Config::generateHtml = TRUE;
QCString Config::htmlOutputDir = "html";
QCString Config::headerFile;
QCString Config::footerFile;
QCString Config::htmlStyleSheet;
bool     Config::htmlAlignMemberFlag = TRUE;
bool     Config::htmlHelpFlag = FALSE;
bool     Config::noIndexFlag = FALSE;
bool     Config::generateLatex = TRUE;
QCString Config::latexOutputDir = "latex";
bool     Config::compactLatexFlag = FALSE;
QCString Config::paperType = "a4wide";
QStrList Config::extraPackageList;
QCString Config::latexHeaderFile;
bool     Config::pdfHyperFlag = FALSE;
bool     Config::usePDFLatexFlag = FALSE;
bool     Config::latexBatchModeFlag = FALSE;
bool     Config::generateRTF = TRUE;
QCString Config::rtfOutputDir = "rtf";
bool     Config::compactRTFFlag = FALSE;
bool     Config::rtfHyperFlag = FALSE;
QCString Config::rtfStylesheetFile;
bool     Config::generateMan = TRUE;
QCString Config::manOutputDir = "man";
QCString Config::manExtension = ".3";
bool     Config::generateXML = FALSE;
bool     Config::preprocessingFlag = TRUE;
bool     Config::macroExpansionFlag = FALSE;
bool     Config::onlyPredefinedFlag = FALSE;
bool     Config::searchIncludeFlag = TRUE;
QStrList Config::includePath;
QStrList Config::includeFilePatternList;
QStrList Config::predefined;
QStrList Config::expandAsDefinedList;
QStrList Config::tagFileList;
QCString Config::genTagFile;
bool     Config::allExtFlag = FALSE;
QCString Config::perlPath = "/usr/bin/perl";
bool     Config::haveDotFlag = FALSE;
bool     Config::classGraphFlag = TRUE;
bool     Config::collGraphFlag = TRUE;
bool     Config::includeGraphFlag = TRUE;
bool     Config::includedByGraphFlag = TRUE;
bool     Config::gfxHierarchyFlag = TRUE;
QCString Config::dotPath;
int      Config::maxDotGraphWidth = 1024;
int      Config::maxDotGraphHeight = 1024;
bool     Config::searchEngineFlag = FALSE;
QCString Config::cgiName = "search.cgi";
QCString Config::cgiURL;
QCString Config::docURL;
QCString Config::docAbsPath;
QCString Config::binAbsPath = "/usr/local/bin/";
QStrList Config::extDocPathList;

/* -----------------------------------------------------------------
 *
 *	static variables
 */

struct ConfigFileState
{
  int lineNr;
  FILE *filePtr;
  YY_BUFFER_STATE oldState;
  YY_BUFFER_STATE newState;
  QCString fileName;
};  

static const char       *inputString;
static int	         inputPosition;
static int               yyLineNr;
static QCString          yyFileName;
static QCString          tmpString;
static QCString         *s=0;
static bool             *b=0;
static QStrList         *l=0;
static int               lastState;
static QCString          elemStr;
static QCString          includeName;
static QStrList          includePathList;
static QStack<ConfigFileState> includeStack;  
static int               includeDepth;

static QCString     tabSizeString;
static QCString     colsInAlphaIndexString;
static QCString     maxDotGraphWidthString;
static QCString     maxDotGraphHeightString;

/* -----------------------------------------------------------------
 */
#undef	YY_INPUT
#define	YY_INPUT(buf,result,max_size) result=yyread(buf,max_size);

static int yyread(char *buf,int max_size)
{
    // no file included
    if (includeStack.isEmpty()) 
    {
        int c=0;
	while( c < max_size && inputString[inputPosition] )
	{
	      *buf = inputString[inputPosition++] ;
	      c++; buf++;
  	}
	return c;
    } 
    else 
    {
        //assert(includeStack.current()->newState==YY_CURRENT_BUFFER);
	return fread(buf,1,max_size,includeStack.current()->filePtr);
    }
}


static FILE *tryPath(const char *path,const char *fileName)
{
  QCString absName=(QCString)path+"/"+fileName;
  QFileInfo fi(absName);
  if (fi.exists() && fi.isFile())
  {
    FILE *f=fopen(absName,"r");
    if (!f) err("Error: could not open file %s for reading\n",absName.data());
    return f;
  }
  return 0;
}

static FILE *findFile(const char *fileName)
{
  char *s=includePathList.first();
  while (s) // try each of the include paths
  {
    FILE *f = tryPath(s,fileName);
    if (f) return f;
    s=includePathList.next();
  } 
  // try cwd if includePathList fails
  return tryPath(".",fileName);
}

static void readIncludeFile(const char *incName)
{
  if (includeDepth==MAX_INCLUDE_DEPTH) {
    err("Error: maximum include depth (%d) reached, %s is not included. Aborting...\n",
	MAX_INCLUDE_DEPTH,incName);
    exit(1);
  } 

  QCString inc = incName;
  inc = inc.stripWhiteSpace();
  uint incLen = inc.length();
  if (inc.at(0)=='"' && inc.at(incLen-1)=='"') // strip quotes
  {
    inc=inc.mid(1,incLen-2);
  }

  FILE *f;

  //printf("Searching for `%s'\n",incFileName.data());
  if ((f=findFile(inc))) // see if the include file can be found
  {
    // For debugging
#if SHOW_INCLUDES
    for (i=0;i<includeStack.count();i++) msg("  ");
    msg("@INCLUDE = %s: parsing...\n",inc.data());
#endif

    // store the state of the old file 
    ConfigFileState *fs=new ConfigFileState;
    fs->oldState=YY_CURRENT_BUFFER;
    fs->lineNr=yyLineNr;
    fs->fileName=yyFileName;
    fs->filePtr=f;
    // push the state on the stack
    includeStack.push(fs);
    // set the scanner to the include file
    yy_switch_to_buffer(yy_create_buffer(f, YY_BUF_SIZE));
    fs->newState=YY_CURRENT_BUFFER;
    yyFileName=inc;
    includeDepth++;
  } 
  else
  {
    err("Error: @INCLUDE = %s: not found!\n",inc.data());
    exit(1);
  }
}


%}

%option noyywrap

%x      Start
%x	SkipComment
%x      GetString
%x      GetBool
%x      GetStrList
%x      GetQuotedString
%x      GetEnvVar
%x      Include

%%

<*>\0x0d
<Start,GetString,GetStrList,GetBool>"#"	{ BEGIN(SkipComment); }
<Start>"PROJECT_NAME"[ \t]*"="           { BEGIN(GetString); s=&Config::projectName; s->resize(0); }
<Start>"PROJECT_NUMBER"[ \t]*"="         { BEGIN(GetString); s=&Config::projectNumber; s->resize(0); }
<Start>"OUTPUT_DIRECTORY"[ \t]*"="       { BEGIN(GetString); s=&Config::outputDir; s->resize(0); }
<Start>"OUTPUT_LANGUAGE"[ \t]*"="        { BEGIN(GetString); s=&Config::outputLanguage; s->resize(0); }
<Start>"EXTRACT_ALL"[ \t]*"="            { BEGIN(GetBool); b=&Config::extractAllFlag; }
<Start>"EXTRACT_PRIVATE"[ \t]*"="        { BEGIN(GetBool); b=&Config::extractPrivateFlag; }
<Start>"EXTRACT_STATIC"[ \t]*"="         { BEGIN(GetBool); b=&Config::extractStaticFlag; }
<Start>"HIDE_UNDOC_MEMBERS"[ \t]*"="     { BEGIN(GetBool); b=&Config::hideMemberFlag; }
<Start>"HIDE_UNDOC_CLASSES"[ \t]*"="     { BEGIN(GetBool); b=&Config::hideClassFlag; }
<Start>"BRIEF_MEMBER_DESC"[ \t]*"="      { BEGIN(GetBool); b=&Config::briefMemDescFlag; }
<Start>"REPEAT_BRIEF"[ \t]*"="           { BEGIN(GetBool); b=&Config::repeatBriefFlag; }
<Start>"ALWAYS_DETAILED_SEC"[ \t]*"="    { BEGIN(GetBool); b=&Config::alwaysDetailsFlag; }
<Start>"FULL_PATH_NAMES"[ \t]*"="        { BEGIN(GetBool); b=&Config::fullPathNameFlag; }
<Start>"STRIP_FROM_PATH"[ \t]*"="        { BEGIN(GetStrList); l=&Config::stripFromPath; l->clear(); elemStr=""; }
<Start>"STRIP_FROM_PATH"[ \t]*"+="       { BEGIN(GetStrList); l=&Config::stripFromPath; elemStr=""; }
<Start>"INTERNAL_DOCS"[ \t]*"="          { BEGIN(GetBool); b=&Config::internalDocsFlag; }
<Start>"CLASS_DIAGRAMS"[ \t]*"="         { BEGIN(GetBool); b=&Config::classDiagramFlag; }
<Start>"SOURCE_BROWSER"[ \t]*"="         { BEGIN(GetBool); b=&Config::sourceBrowseFlag; }
<Start>"INLINE_SOURCES"[ \t]*"="         { BEGIN(GetBool); b=&Config::inlineSourceFlag; }
<Start>"STRIP_CODE_COMMENTS"[ \t]*"="    { BEGIN(GetBool); b=&Config::stripCommentsFlag; }
<Start>"CASE_SENSE_NAMES"[ \t]*"="       { BEGIN(GetBool); b=&Config::caseSensitiveNames; }
<Start>"HIDE_SCOPE_NAMES"[ \t]*"="       { BEGIN(GetBool); b=&Config::hideScopeNames; }
<Start>"VERBATIM_HEADERS"[ \t]*"="       { BEGIN(GetBool); b=&Config::verbatimHeaderFlag; }
<Start>"SHOW_INCLUDE_FILES"[ \t]*"="     { BEGIN(GetBool); b=&Config::showIncFileFlag; }
<Start>"JAVADOC_AUTOBRIEF"[ \t]*"="      { BEGIN(GetBool); b=&Config::autoBriefFlag; }
<Start>"INHERIT_DOCS"[ \t]*"="           { BEGIN(GetBool); b=&Config::inheritDocsFlag; }
<Start>"INLINE_INFO"[ \t]*"="            { BEGIN(GetBool); b=&Config::inlineInfoFlag; }
<Start>"SORT_MEMBER_DOCS"[ \t]*"="       { BEGIN(GetBool); b=&Config::sortMembersFlag; }
<Start>"TAB_SIZE"[ \t]*"="               { BEGIN(GetString); s=&tabSizeString; s->resize(0); }
<Start>"ENABLED_SECTIONS"[ \t]*"="       { BEGIN(GetStrList); l=&Config::sectionFilterList; l->clear(); elemStr=""; }
<Start>"ENABLED_SECTIONS"[ \t]*"+="      { BEGIN(GetStrList); l=&Config::sectionFilterList; elemStr=""; }
<Start>"GENERATE_TODOLIST"[ \t]*"="      { BEGIN(GetBool); b=&Config::generateTodoList; }
<Start>"GENERATE_TESTLIST"[ \t]*"="      { BEGIN(GetBool); b=&Config::generateTestList; }
<Start>"QUIET"[ \t]*"="                  { BEGIN(GetBool); b=&Config::quietFlag; }
<Start>"WARNINGS"[ \t]*"="               { BEGIN(GetBool); b=&Config::warningFlag; }
<Start>"WARN_IF_UNDOCUMENTED"[ \t]*"="   { BEGIN(GetBool); b=&Config::warningUndocFlag; }
<Start>"WARN_FORMAT"[ \t]*"="            { BEGIN(GetString); s=&Config::warnFormat; s->resize(0); }
<Start>"INPUT"[ \t]*"="                  { BEGIN(GetStrList); l=&Config::inputSources; l->clear(); elemStr=""; }
<Start>"INPUT"[ \t]*"+="                 { BEGIN(GetStrList); l=&Config::inputSources; elemStr=""; }
<Start>"FILE_PATTERNS"[ \t]*"="          { BEGIN(GetStrList); l=&Config::filePatternList; l->clear(); elemStr=""; }
<Start>"FILE_PATTERNS"[ \t]*"+="         { BEGIN(GetStrList); l=&Config::filePatternList; elemStr=""; }
<Start>"RECURSIVE"[ \t]*"="              { BEGIN(GetBool); b=&Config::recursiveFlag; }
<Start>"EXCLUDE"[ \t]*"="                { BEGIN(GetStrList); l=&Config::excludeSources; l->clear(); elemStr=""; }
<Start>"EXCLUDE"[ \t]*"+="               { BEGIN(GetStrList); l=&Config::excludeSources; elemStr=""; }
<Start>"EXCLUDE_PATTERNS"[ \t]*"="       { BEGIN(GetStrList); l=&Config::excludePatternList; l->clear(); elemStr=""; }
<Start>"EXCLUDE_PATTERNS"[ \t]*"+="      { BEGIN(GetStrList); l=&Config::excludePatternList; elemStr=""; }
<Start>"EXAMPLE_PATH"[ \t]*"="           { BEGIN(GetStrList); l=&Config::examplePath; l->clear(); elemStr=""; }
<Start>"EXAMPLE_PATH"[ \t]*"+="          { BEGIN(GetStrList); l=&Config::examplePath; elemStr=""; }
<Start>"EXAMPLE_PATTERNS"[ \t]*"="       { BEGIN(GetStrList); l=&Config::examplePatternList; l->clear(); elemStr=""; }
<Start>"EXAMPLE_PATTERNS"[ \t]*"+="      { BEGIN(GetStrList); l=&Config::examplePatternList; elemStr=""; }
<Start>"IMAGE_PATH"[ \t]*"="             { BEGIN(GetStrList); l=&Config::imagePath; l->clear(); elemStr=""; }
<Start>"IMAGE_PATH"[ \t]*"+="            { BEGIN(GetStrList); l=&Config::imagePath; elemStr=""; }
<Start>"INPUT_FILTER"[ \t]*"="           { BEGIN(GetString); s=&Config::inputFilter; s->resize(0); }
<Start>"ALPHABETICAL_INDEX"[ \t]*"="     { BEGIN(GetBool); b=&Config::alphaIndexFlag; }
<Start>"COLS_IN_ALPHA_INDEX"[ \t]*"="    { BEGIN(GetString); s=&colsInAlphaIndexString; s->resize(0); }
<Start>"IGNORE_PREFIX"[ \t]*"="          { BEGIN(GetStrList); l=&Config::ignorePrefixList; l->clear(); elemStr=""; }
<Start>"IGNORE_PREFIX"[ \t]*"+="         { BEGIN(GetStrList); l=&Config::ignorePrefixList; elemStr=""; }
<Start>"GENERATE_HTML"[ \t]*"="          { BEGIN(GetBool); b=&Config::generateHtml; }
<Start>"HTML_OUTPUT"[ \t]*"="            { BEGIN(GetString); s=&Config::htmlOutputDir; s->resize(0); }
<Start>"HTML_HEADER"[ \t]*"="            { BEGIN(GetString); s=&Config::headerFile; s->resize(0); }
<Start>"HTML_FOOTER"[ \t]*"="            { BEGIN(GetString); s=&Config::footerFile; s->resize(0); }
<Start>"HTML_STYLESHEET"[ \t]*"="        { BEGIN(GetString); s=&Config::htmlStyleSheet; s->resize(0); }
<Start>"HTML_ALIGN_MEMBERS"[ \t]*"="     { BEGIN(GetBool); b=&Config::htmlAlignMemberFlag; }
<Start>"GENERATE_HTMLHELP"[ \t]*"="      { BEGIN(GetBool); b=&Config::htmlHelpFlag; }
<Start>"DISABLE_INDEX"[ \t]*"="          { BEGIN(GetBool); b=&Config::noIndexFlag; }
<Start>"GENERATE_LATEX"[ \t]*"="         { BEGIN(GetBool); b=&Config::generateLatex; }
<Start>"LATEX_OUTPUT"[ \t]*"="           { BEGIN(GetString); s=&Config::latexOutputDir; s->resize(0); }
<Start>"COMPACT_LATEX"[ \t]*"="          { BEGIN(GetBool); b=&Config::compactLatexFlag; }
<Start>"PAPER_TYPE"[ \t]*"="             { BEGIN(GetString); s=&Config::paperType; s->resize(0); }
<Start>"EXTRA_PACKAGES"[ \t]*"="         { BEGIN(GetStrList); l=&Config::extraPackageList; l->clear(); elemStr=""; }
<Start>"EXTRA_PACKAGES"[ \t]*"+="        { BEGIN(GetStrList); l=&Config::extraPackageList; elemStr=""; }
<Start>"LATEX_HEADER"[ \t]*"="           { BEGIN(GetString); s=&Config::latexHeaderFile; s->resize(0); }
<Start>"PDF_HYPERLINKS"[ \t]*"="         { BEGIN(GetBool); b=&Config::pdfHyperFlag; }
<Start>"USE_PDFLATEX"[ \t]*"="           { BEGIN(GetBool); b=&Config::usePDFLatexFlag; }
<Start>"LATEX_BATCHMODE"[ \t]*"="        { BEGIN(GetBool); b=&Config::latexBatchModeFlag; }
<Start>"GENERATE_RTF"[ \t]*"="           { BEGIN(GetBool); b=&Config::generateRTF; }
<Start>"RTF_OUTPUT"[ \t]*"="             { BEGIN(GetString); s=&Config::rtfOutputDir; s->resize(0); }
<Start>"COMPACT_RTF"[ \t]*"="            { BEGIN(GetBool); b=&Config::compactRTFFlag; }
<Start>"RTF_HYPERLINKS"[ \t]*"="         { BEGIN(GetBool); b=&Config::rtfHyperFlag; }
<Start>"RTF_STYLESHEET_FILE"[ \t]*"="    { BEGIN(GetString); s=&Config::rtfStylesheetFile; s->resize(0); }
<Start>"GENERATE_MAN"[ \t]*"="           { BEGIN(GetBool); b=&Config::generateMan; }
<Start>"MAN_OUTPUT"[ \t]*"="             { BEGIN(GetString); s=&Config::manOutputDir; s->resize(0); }
<Start>"MAN_EXTENSION"[ \t]*"="          { BEGIN(GetString); s=&Config::manExtension; s->resize(0); }
<Start>"GENERATE_XML"[ \t]*"="           { BEGIN(GetBool); b=&Config::generateXML; }
<Start>"ENABLE_PREPROCESSING"[ \t]*"="   { BEGIN(GetBool); b=&Config::preprocessingFlag; }
<Start>"MACRO_EXPANSION"[ \t]*"="        { BEGIN(GetBool); b=&Config::macroExpansionFlag; }
<Start>"EXPAND_ONLY_PREDEF"[ \t]*"="     { BEGIN(GetBool); b=&Config::onlyPredefinedFlag; }
<Start>"SEARCH_INCLUDES"[ \t]*"="        { BEGIN(GetBool); b=&Config::searchIncludeFlag; }
<Start>"INCLUDE_PATH"[ \t]*"="           { BEGIN(GetStrList); l=&Config::includePath; l->clear(); elemStr=""; }
<Start>"INCLUDE_PATH"[ \t]*"+="          { BEGIN(GetStrList); l=&Config::includePath; elemStr=""; }
<Start>"INCLUDE_FILE_PATTERNS"[ \t]*"="  { BEGIN(GetStrList); l=&Config::includeFilePatternList; l->clear(); elemStr=""; }
<Start>"INCLUDE_FILE_PATTERNS"[ \t]*"+=" { BEGIN(GetStrList); l=&Config::includeFilePatternList; elemStr=""; }
<Start>"PREDEFINED"[ \t]*"="             { BEGIN(GetStrList); l=&Config::predefined; l->clear(); elemStr=""; }
<Start>"PREDEFINED"[ \t]*"+="            { BEGIN(GetStrList); l=&Config::predefined; elemStr=""; }
<Start>"EXPAND_AS_DEFINED"[ \t]*"="      { BEGIN(GetStrList); l=&Config::expandAsDefinedList; l->clear(); elemStr=""; }
<Start>"EXPAND_AS_DEFINED"[ \t]*"+="     { BEGIN(GetStrList); l=&Config::expandAsDefinedList; elemStr=""; }
<Start>"TAGFILES"[ \t]*"="               { BEGIN(GetStrList); l=&Config::tagFileList; l->clear(); elemStr=""; }
<Start>"TAGFILES"[ \t]*"+="              { BEGIN(GetStrList); l=&Config::tagFileList; elemStr=""; }
<Start>"GENERATE_TAGFILE"[ \t]*"="       { BEGIN(GetString); s=&Config::genTagFile; s->resize(0); }
<Start>"ALLEXTERNALS"[ \t]*"="           { BEGIN(GetBool); b=&Config::allExtFlag; }
<Start>"PERL_PATH"[ \t]*"="              { BEGIN(GetString); s=&Config::perlPath; s->resize(0); }
<Start>"HAVE_DOT"[ \t]*"="               { BEGIN(GetBool); b=&Config::haveDotFlag; }
<Start>"CLASS_GRAPH"[ \t]*"="            { BEGIN(GetBool); b=&Config::classGraphFlag; }
<Start>"COLLABORATION_GRAPH"[ \t]*"="    { BEGIN(GetBool); b=&Config::collGraphFlag; }
<Start>"INCLUDE_GRAPH"[ \t]*"="          { BEGIN(GetBool); b=&Config::includeGraphFlag; }
<Start>"INCLUDED_BY_GRAPH"[ \t]*"="      { BEGIN(GetBool); b=&Config::includedByGraphFlag; }
<Start>"GRAPHICAL_HIERARCHY"[ \t]*"="    { BEGIN(GetBool); b=&Config::gfxHierarchyFlag; }
<Start>"DOT_PATH"[ \t]*"="               { BEGIN(GetString); s=&Config::dotPath; s->resize(0); }
<Start>"MAX_DOT_GRAPH_WIDTH"[ \t]*"="    { BEGIN(GetString); s=&maxDotGraphWidthString; s->resize(0); }
<Start>"MAX_DOT_GRAPH_HEIGHT"[ \t]*"="   { BEGIN(GetString); s=&maxDotGraphHeightString; s->resize(0); }
<Start>"SEARCHENGINE"[ \t]*"="           { BEGIN(GetBool); b=&Config::searchEngineFlag; }
<Start>"CGI_NAME"[ \t]*"="               { BEGIN(GetString); s=&Config::cgiName; s->resize(0); }
<Start>"CGI_URL"[ \t]*"="                { BEGIN(GetString); s=&Config::cgiURL; s->resize(0); }
<Start>"DOC_URL"[ \t]*"="                { BEGIN(GetString); s=&Config::docURL; s->resize(0); }
<Start>"DOC_ABSPATH"[ \t]*"="            { BEGIN(GetString); s=&Config::docAbsPath; s->resize(0); }
<Start>"BIN_ABSPATH"[ \t]*"="            { BEGIN(GetString); s=&Config::binAbsPath; s->resize(0); }
<Start>"EXT_DOC_PATHS"[ \t]*"="          { BEGIN(GetStrList); l=&Config::extDocPathList; l->clear(); elemStr=""; }
<Start>"EXT_DOC_PATHS"[ \t]*"+="         { BEGIN(GetStrList); l=&Config::extDocPathList; elemStr=""; }

<Start>"@INCLUDE_PATH"[ \t]*"=" 	{ BEGIN(GetStrList); l=&includePathList; l->clear(); elemStr=""; }
  /* include a config file */
<Start>"@INCLUDE"[ \t]*"="     		{ BEGIN(Include);}
<Include>([^ \"\t\r\n]+)|("\""[^\n\"]+"\"") { 
  					  readIncludeFile(yytext); 
  					  BEGIN(Start);
					}
<<EOF>>					{
                                          //printf("End of include file\n");
					  //printf("Include stack depth=%d\n",g_includeStack.count());
                                          if (includeStack.isEmpty())
					  {
					    //printf("Terminating scanner!\n");
					    yyterminate();
					  }
					  else
					  {
					    ConfigFileState *fs=includeStack.pop();
					    fclose(fs->filePtr);
					    YY_BUFFER_STATE oldBuf = YY_CURRENT_BUFFER;
					    yy_switch_to_buffer( fs->oldState );
					    yy_delete_buffer( oldBuf );
					    yyLineNr=fs->lineNr;
					    yyFileName=fs->fileName;
					    delete fs; fs=0;
                                            includeDepth--;
					  }
  					}

<Start>[a-z_A-Z0-9]+			{ err("Warning: ignoring unknown tag `%s' at line %d, file %s\n",yytext,yyLineNr,yyFileName.data()); }
<GetString,GetBool>\n			{ yyLineNr++; BEGIN(Start); }
<GetStrList>\n				{ 
  					  yyLineNr++; 
					  if (!elemStr.isEmpty())
					  {
					    //printf("elemStr1=`%s'\n",elemStr.data());
					    l->append(elemStr);
					  }
					  BEGIN(Start); 
					}
<GetStrList>[ \t]+			{
  				          if (!elemStr.isEmpty())
					  {
					    //printf("elemStr2=`%s'\n",elemStr.data());
  					    l->append(elemStr);
					  }
					  elemStr.resize(0);
  					}
<GetString>[^ \"\t\r\n]+		{ (*s)+=yytext; }
<GetString,GetStrList>"\""		{ lastState=YY_START;
  					  BEGIN(GetQuotedString); 
                                          tmpString.resize(0); 
					}
<GetQuotedString>"\""|"\n" 		{ 
  					  //printf("Quoted String = `%s'\n",tmpString.data());
  					  if (lastState==GetString)
					    (*s)+=tmpString;
					  else
					    elemStr+=tmpString;
					  if (*yytext=='\n')
					  {
					    err("Warning: Missing end quote (\") on line %d, file %s\n",yyLineNr,yyFileName.data());
					    yyLineNr++;
					  }
					  BEGIN(lastState);
  					}
<GetQuotedString>"\\\""			{
  					  tmpString+='"';
  					}
<GetQuotedString>.			{ tmpString+=*yytext; }
<GetBool>[a-zA-Z]+			{ 
  					  QCString bs=yytext; 
  					  bs=bs.upper();
  					  if (bs=="YES")
					    *b=TRUE;
					  else if (bs=="NO")
					    *b=FALSE;
					  else 
					  {
					    *b=FALSE; 
					    warn_cont("Warning: Invalid value `%s' for "
						 "boolean tag in line %d, file %s; use YES or NO\n",
						 bs.data(),yyLineNr,yyFileName.data());
					  }
					}
<GetStrList>[^ \#\"\t\r\n]+		{
  					  elemStr+=yytext;
  					}
<SkipComment>\n				{ yyLineNr++; BEGIN(Start); }
<SkipComment>\\[ \r\t]*\n		{ yyLineNr++; BEGIN(Start); }
<*>\\[ \r\t]*\n				{ yyLineNr++; }
<*>.					
<*>\n					{ yyLineNr++ ; }

%%

/*@ ----------------------------------------------------------------------------
 */


void dumpConfig()
{
  printf("# General configuration options\n");
  printf("projectName=`%s'\n",Config::projectName.data());
  printf("projectNumber=`%s'\n",Config::projectNumber.data());
  printf("outputDir=`%s'\n",Config::outputDir.data());
  printf("outputLanguage=`%s'\n",Config::outputLanguage.data());
  printf("extractAllFlag=`%d'\n",Config::extractAllFlag);
  printf("extractPrivateFlag=`%d'\n",Config::extractPrivateFlag);
  printf("extractStaticFlag=`%d'\n",Config::extractStaticFlag);
  printf("hideMemberFlag=`%d'\n",Config::hideMemberFlag);
  printf("hideClassFlag=`%d'\n",Config::hideClassFlag);
  printf("briefMemDescFlag=`%d'\n",Config::briefMemDescFlag);
  printf("repeatBriefFlag=`%d'\n",Config::repeatBriefFlag);
  printf("alwaysDetailsFlag=`%d'\n",Config::alwaysDetailsFlag);
  printf("fullPathNameFlag=`%d'\n",Config::fullPathNameFlag);
  {
    char *is=Config::stripFromPath.first();
    while (is)
    {
      printf("stripFromPath=`%s'\n",is);
      is=Config::stripFromPath.next();
    }
  }
  printf("internalDocsFlag=`%d'\n",Config::internalDocsFlag);
  printf("classDiagramFlag=`%d'\n",Config::classDiagramFlag);
  printf("sourceBrowseFlag=`%d'\n",Config::sourceBrowseFlag);
  printf("inlineSourceFlag=`%d'\n",Config::inlineSourceFlag);
  printf("stripCommentsFlag=`%d'\n",Config::stripCommentsFlag);
  printf("caseSensitiveNames=`%d'\n",Config::caseSensitiveNames);
  printf("hideScopeNames=`%d'\n",Config::hideScopeNames);
  printf("verbatimHeaderFlag=`%d'\n",Config::verbatimHeaderFlag);
  printf("showIncFileFlag=`%d'\n",Config::showIncFileFlag);
  printf("autoBriefFlag=`%d'\n",Config::autoBriefFlag);
  printf("inheritDocsFlag=`%d'\n",Config::inheritDocsFlag);
  printf("inlineInfoFlag=`%d'\n",Config::inlineInfoFlag);
  printf("sortMembersFlag=`%d'\n",Config::sortMembersFlag);
  printf("tabSize=`%d'\n",Config::tabSize);
  {
    char *is=Config::sectionFilterList.first();
    while (is)
    {
      printf("sectionFilterList=`%s'\n",is);
      is=Config::sectionFilterList.next();
    }
  }
  printf("generateTodoList=`%d'\n",Config::generateTodoList);
  printf("generateTestList=`%d'\n",Config::generateTestList);
  printf("# configuration options related to warning and progress messages\n");
  printf("quietFlag=`%d'\n",Config::quietFlag);
  printf("warningFlag=`%d'\n",Config::warningFlag);
  printf("warningUndocFlag=`%d'\n",Config::warningUndocFlag);
  printf("warnFormat=`%s'\n",Config::warnFormat.data());
  printf("# configuration options related to the input files\n");
  {
    char *is=Config::inputSources.first();
    while (is)
    {
      printf("inputSources=`%s'\n",is);
      is=Config::inputSources.next();
    }
  }
  {
    char *is=Config::filePatternList.first();
    while (is)
    {
      printf("filePatternList=`%s'\n",is);
      is=Config::filePatternList.next();
    }
  }
  printf("recursiveFlag=`%d'\n",Config::recursiveFlag);
  {
    char *is=Config::excludeSources.first();
    while (is)
    {
      printf("excludeSources=`%s'\n",is);
      is=Config::excludeSources.next();
    }
  }
  {
    char *is=Config::excludePatternList.first();
    while (is)
    {
      printf("excludePatternList=`%s'\n",is);
      is=Config::excludePatternList.next();
    }
  }
  {
    char *is=Config::examplePath.first();
    while (is)
    {
      printf("examplePath=`%s'\n",is);
      is=Config::examplePath.next();
    }
  }
  {
    char *is=Config::examplePatternList.first();
    while (is)
    {
      printf("examplePatternList=`%s'\n",is);
      is=Config::examplePatternList.next();
    }
  }
  {
    char *is=Config::imagePath.first();
    while (is)
    {
      printf("imagePath=`%s'\n",is);
      is=Config::imagePath.next();
    }
  }
  printf("inputFilter=`%s'\n",Config::inputFilter.data());
  printf("# configuration options related to the alphabetical class index\n");
  printf("alphaIndexFlag=`%d'\n",Config::alphaIndexFlag);
  printf("colsInAlphaIndex=`%d'\n",Config::colsInAlphaIndex);
  {
    char *is=Config::ignorePrefixList.first();
    while (is)
    {
      printf("ignorePrefixList=`%s'\n",is);
      is=Config::ignorePrefixList.next();
    }
  }
  printf("# configuration options related to the HTML output\n");
  printf("generateHtml=`%d'\n",Config::generateHtml);
  printf("htmlOutputDir=`%s'\n",Config::htmlOutputDir.data());
  printf("headerFile=`%s'\n",Config::headerFile.data());
  printf("footerFile=`%s'\n",Config::footerFile.data());
  printf("htmlStyleSheet=`%s'\n",Config::htmlStyleSheet.data());
  printf("htmlAlignMemberFlag=`%d'\n",Config::htmlAlignMemberFlag);
  printf("htmlHelpFlag=`%d'\n",Config::htmlHelpFlag);
  printf("noIndexFlag=`%d'\n",Config::noIndexFlag);
  printf("# configuration options related to the LaTeX output\n");
  printf("generateLatex=`%d'\n",Config::generateLatex);
  printf("latexOutputDir=`%s'\n",Config::latexOutputDir.data());
  printf("compactLatexFlag=`%d'\n",Config::compactLatexFlag);
  printf("paperType=`%s'\n",Config::paperType.data());
  {
    char *is=Config::extraPackageList.first();
    while (is)
    {
      printf("extraPackageList=`%s'\n",is);
      is=Config::extraPackageList.next();
    }
  }
  printf("latexHeaderFile=`%s'\n",Config::latexHeaderFile.data());
  printf("pdfHyperFlag=`%d'\n",Config::pdfHyperFlag);
  printf("usePDFLatexFlag=`%d'\n",Config::usePDFLatexFlag);
  printf("latexBatchModeFlag=`%d'\n",Config::latexBatchModeFlag);
  printf("# configuration options related to the RTF output\n");
  printf("generateRTF=`%d'\n",Config::generateRTF);
  printf("rtfOutputDir=`%s'\n",Config::rtfOutputDir.data());
  printf("compactRTFFlag=`%d'\n",Config::compactRTFFlag);
  printf("rtfHyperFlag=`%d'\n",Config::rtfHyperFlag);
  printf("rtfStylesheetFile=`%s'\n",Config::rtfStylesheetFile.data());
  printf("# configuration options related to the man page output\n");
  printf("generateMan=`%d'\n",Config::generateMan);
  printf("manOutputDir=`%s'\n",Config::manOutputDir.data());
  printf("manExtension=`%s'\n",Config::manExtension.data());
  printf("# configuration options related to the XML output\n");
  printf("generateXML=`%d'\n",Config::generateXML);
  printf("# Configuration options related to the preprocessor   \n");
  printf("preprocessingFlag=`%d'\n",Config::preprocessingFlag);
  printf("macroExpansionFlag=`%d'\n",Config::macroExpansionFlag);
  printf("onlyPredefinedFlag=`%d'\n",Config::onlyPredefinedFlag);
  printf("searchIncludeFlag=`%d'\n",Config::searchIncludeFlag);
  {
    char *is=Config::includePath.first();
    while (is)
    {
      printf("includePath=`%s'\n",is);
      is=Config::includePath.next();
    }
  }
  {
    char *is=Config::includeFilePatternList.first();
    while (is)
    {
      printf("includeFilePatternList=`%s'\n",is);
      is=Config::includeFilePatternList.next();
    }
  }
  {
    char *is=Config::predefined.first();
    while (is)
    {
      printf("predefined=`%s'\n",is);
      is=Config::predefined.next();
    }
  }
  {
    char *is=Config::expandAsDefinedList.first();
    while (is)
    {
      printf("expandAsDefinedList=`%s'\n",is);
      is=Config::expandAsDefinedList.next();
    }
  }
  printf("# Configuration::addtions related to external references   \n");
  {
    char *is=Config::tagFileList.first();
    while (is)
    {
      printf("tagFileList=`%s'\n",is);
      is=Config::tagFileList.next();
    }
  }
  printf("genTagFile=`%s'\n",Config::genTagFile.data());
  printf("allExtFlag=`%d'\n",Config::allExtFlag);
  printf("perlPath=`%s'\n",Config::perlPath.data());
  printf("# Configuration options related to the dot tool   \n");
  printf("haveDotFlag=`%d'\n",Config::haveDotFlag);
  printf("classGraphFlag=`%d'\n",Config::classGraphFlag);
  printf("collGraphFlag=`%d'\n",Config::collGraphFlag);
  printf("includeGraphFlag=`%d'\n",Config::includeGraphFlag);
  printf("includedByGraphFlag=`%d'\n",Config::includedByGraphFlag);
  printf("gfxHierarchyFlag=`%d'\n",Config::gfxHierarchyFlag);
  printf("dotPath=`%s'\n",Config::dotPath.data());
  printf("maxDotGraphWidth=`%d'\n",Config::maxDotGraphWidth);
  printf("maxDotGraphHeight=`%d'\n",Config::maxDotGraphHeight);
  printf("# Configuration::addtions related to the search engine   \n");
  printf("searchEngineFlag=`%d'\n",Config::searchEngineFlag);
  printf("cgiName=`%s'\n",Config::cgiName.data());
  printf("cgiURL=`%s'\n",Config::cgiURL.data());
  printf("docURL=`%s'\n",Config::docURL.data());
  printf("docAbsPath=`%s'\n",Config::docAbsPath.data());
  printf("binAbsPath=`%s'\n",Config::binAbsPath.data());
  {
    char *is=Config::extDocPathList.first();
    while (is)
    {
      printf("extDocPathList=`%s'\n",is);
      is=Config::extDocPathList.next();
    }
  }
}

void Config::init()
{
  Config::projectName.resize(0);
  Config::projectNumber.resize(0);
  Config::outputDir.resize(0);
  Config::outputLanguage = "English";
  Config::extractAllFlag = FALSE;
  Config::extractPrivateFlag = FALSE;
  Config::extractStaticFlag = FALSE;
  Config::hideMemberFlag = FALSE;
  Config::hideClassFlag = FALSE;
  Config::briefMemDescFlag = TRUE;
  Config::repeatBriefFlag = TRUE;
  Config::alwaysDetailsFlag = FALSE;
  Config::fullPathNameFlag = FALSE;
  Config::stripFromPath.clear();
  Config::internalDocsFlag = FALSE;
  Config::classDiagramFlag = TRUE;
  Config::sourceBrowseFlag = FALSE;
  Config::inlineSourceFlag = FALSE;
  Config::stripCommentsFlag = TRUE;
  Config::caseSensitiveNames = TRUE;
  Config::hideScopeNames = FALSE;
  Config::verbatimHeaderFlag = TRUE;
  Config::showIncFileFlag = TRUE;
  Config::autoBriefFlag = TRUE;
  Config::inheritDocsFlag = TRUE;
  Config::inlineInfoFlag = TRUE;
  Config::sortMembersFlag = TRUE;
  Config::tabSize = 8;
  Config::sectionFilterList.clear();
  Config::generateTodoList = TRUE;
  Config::generateTestList = TRUE;
  Config::quietFlag = FALSE;
  Config::warningFlag = TRUE;
  Config::warningUndocFlag = TRUE;
  Config::warnFormat = "$file:$line: $text";
  Config::inputSources.clear();
  Config::filePatternList.clear();
  Config::recursiveFlag = FALSE;
  Config::excludeSources.clear();
  Config::excludePatternList.clear();
  Config::examplePath.clear();
  Config::examplePatternList.clear();
  Config::imagePath.clear();
  Config::inputFilter.resize(0);
  Config::alphaIndexFlag = FALSE;
  Config::colsInAlphaIndex = 5;
  Config::ignorePrefixList.clear();
  Config::generateHtml = TRUE;
  Config::htmlOutputDir = "html";
  Config::headerFile.resize(0);
  Config::footerFile.resize(0);
  Config::htmlStyleSheet.resize(0);
  Config::htmlAlignMemberFlag = TRUE;
  Config::htmlHelpFlag = FALSE;
  Config::noIndexFlag = FALSE;
  Config::generateLatex = TRUE;
  Config::latexOutputDir = "latex";
  Config::compactLatexFlag = FALSE;
  Config::paperType = "a4wide";
  Config::extraPackageList.clear();
  Config::latexHeaderFile.resize(0);
  Config::pdfHyperFlag = FALSE;
  Config::usePDFLatexFlag = FALSE;
  Config::latexBatchModeFlag = FALSE;
  Config::generateRTF = TRUE;
  Config::rtfOutputDir = "rtf";
  Config::compactRTFFlag = FALSE;
  Config::rtfHyperFlag = FALSE;
  Config::rtfStylesheetFile.resize(0);
  Config::generateMan = TRUE;
  Config::manOutputDir = "man";
  Config::manExtension = ".3";
  Config::generateXML = FALSE;
  Config::preprocessingFlag = TRUE;
  Config::macroExpansionFlag = FALSE;
  Config::onlyPredefinedFlag = FALSE;
  Config::searchIncludeFlag = TRUE;
  Config::includePath.clear();
  Config::includeFilePatternList.clear();
  Config::predefined.clear();
  Config::expandAsDefinedList.clear();
  Config::tagFileList.clear();
  Config::genTagFile.resize(0);
  Config::allExtFlag = FALSE;
  Config::perlPath = "/usr/bin/perl";
  Config::haveDotFlag = FALSE;
  Config::classGraphFlag = TRUE;
  Config::collGraphFlag = TRUE;
  Config::includeGraphFlag = TRUE;
  Config::includedByGraphFlag = TRUE;
  Config::gfxHierarchyFlag = TRUE;
  Config::dotPath.resize(0);
  Config::maxDotGraphWidth = 1024;
  Config::maxDotGraphHeight = 1024;
  Config::searchEngineFlag = FALSE;
  Config::cgiName = "search.cgi";
  Config::cgiURL.resize(0);
  Config::docURL.resize(0);
  Config::docAbsPath.resize(0);
  Config::binAbsPath = "/usr/local/bin/";
  Config::extDocPathList.clear();
}

static void writeBoolValue(QTextStream &t,bool v)
{
  if (v) t << "YES"; else t << "NO";
}

static void writeIntValue(QTextStream &t,int i)
{
  t << i;
}

static void writeStringValue(QTextStream &t,QCString &s)
{
  const char *p=s.data();
  char c;
  bool hasBlanks=FALSE;
  if (p)
  {
    while ((c=*p++)!=0 && !hasBlanks) hasBlanks = (c==' ' || c=='\n' || c=='\t');
    if (hasBlanks) 
      t << "\"" << s << "\"";
    else
      t << s;
  }
}

static void writeStringList(QTextStream &t,QStrList &l)
{
  const char *p = l.first();
  bool first=TRUE;
  while (p)
  {
    char c;
    const char *s=p;
    bool hasBlanks=FALSE;
    while ((c=*p++)!=0 && !hasBlanks) hasBlanks = (c==' ' || c=='\n' || c=='\t');
    if (!first) t << "                         ";
    first=FALSE;
    if (hasBlanks) t << "\"" << s << "\""; else t << s;
    p = l.next();
    if (p) t << " \\" << endl;
  }
}

void writeTemplateConfig(QFile *f,bool sl)
{
  QTextStream t(f);
#ifdef DOXYWIZARD
  t << "# Doxygen configuration generated by Doxywizard version " << versionString << endl;
#else
  t << "# Doxyfile " << versionString << endl << endl;
#endif
  if (!sl)
  {
    t << "# This file describes the settings to be used by doxygen for a project\n";
    t << "#\n";
    t << "# All text after a hash (#) is considered a comment and will be ignored\n";
    t << "# The format is:\n";
    t << "#       TAG = value [value, ...]\n";
    t << "# For lists items can also be appended using:\n";
    t << "#       TAG += value [value, ...]\n";
    t << "# Values that contain spaces should be placed between quotes (\" \")\n";
  }
  if (!sl)
  {
    t << "\n";
  }
  t << "#---------------------------------------------------------------------------\n";
  t << "# General configuration options\n";
  t << "#---------------------------------------------------------------------------\n";
  if (!sl)
  {
    t << "\n";
    t << "# The PROJECT_NAME tag is a single word (or a sequence of words surrounded \n";
    t << "# by quotes) that should identify the project. \n";
    t << "\n";
  }
  t << "PROJECT_NAME           = ";
  writeStringValue(t,Config::projectName);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The PROJECT_NUMBER tag can be used to enter a project or revision number. \n";
    t << "# This could be handy for archiving the generated documentation or \n";
    t << "# if some version control system is used.\n";
    t << "\n";
  }
  t << "PROJECT_NUMBER         = ";
  writeStringValue(t,Config::projectNumber);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The OUTPUT_DIRECTORY tag is used to specify the (relative or absolute) \n";
    t << "# base path where the generated documentation will be put. \n";
    t << "# If a relative path is entered, it will be relative to the location \n";
    t << "# where doxygen was started. If left blank the current directory will be used.\n";
    t << "\n";
  }
  t << "OUTPUT_DIRECTORY       = ";
  writeStringValue(t,Config::outputDir);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The OUTPUT_LANGUAGE tag is used to specify the language in which all \n";
    t << "# documentation generated by doxygen is written. Doxygen will use this \n";
    t << "# information to generate all constant output in the proper language. \n";
    t << "# The default language is English, other supported languages are: \n";
    t << "# Dutch, French, Italian, Czech, Swedish, German, Finnish, Japanese, \n";
    t << "# Spanish, Russian, Croatian, Polish, and Portuguese.\n";
    t << "\n";
  }
  t << "OUTPUT_LANGUAGE        = ";
  writeStringValue(t,Config::outputLanguage);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the EXTRACT_ALL tag is set to YES doxygen will assume all entities in \n";
    t << "# documentation are documented, even if no documentation was available. \n";
    t << "# Private class members and static file members will be hidden unless \n";
    t << "# the EXTRACT_PRIVATE and EXTRACT_STATIC tags are set to YES \n";
    t << "\n";
  }
  t << "EXTRACT_ALL            = ";
  writeBoolValue(t,Config::extractAllFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the EXTRACT_PRIVATE tag is set to YES all private members of a class \n";
    t << "# will be included in the documentation. \n";
    t << "\n";
  }
  t << "EXTRACT_PRIVATE        = ";
  writeBoolValue(t,Config::extractPrivateFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the EXTRACT_STATIC tag is set to YES all static members of a file \n";
    t << "# will be included in the documentation. \n";
    t << "\n";
  }
  t << "EXTRACT_STATIC         = ";
  writeBoolValue(t,Config::extractStaticFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the HIDE_UNDOC_MEMBERS tag is set to YES, Doxygen will hide all \n";
    t << "# undocumented members of documented classes, files or namespaces. \n";
    t << "# If set to NO (the default) these members will be included in the \n";
    t << "# various overviews, but no documentation section is generated. \n";
    t << "# This option has no effect if EXTRACT_ALL is enabled. \n";
    t << "\n";
  }
  t << "HIDE_UNDOC_MEMBERS     = ";
  writeBoolValue(t,Config::hideMemberFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the HIDE_UNDOC_CLASSES tag is set to YES, Doxygen will hide all \n";
    t << "# undocumented classes that are normally visible in the class hierarchy. \n";
    t << "# If set to NO (the default) these class will be included in the various \n";
    t << "# overviews. This option has no effect if EXTRACT_ALL is enabled. \n";
    t << "\n";
  }
  t << "HIDE_UNDOC_CLASSES     = ";
  writeBoolValue(t,Config::hideClassFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the BRIEF_MEMBER_DESC tag is set to YES (the default) Doxygen will \n";
    t << "# include brief member descriptions after the members that are listed in \n";
    t << "# the file and class documentation (similar to JavaDoc). \n";
    t << "# Set to NO to disable this. \n";
    t << "\n";
  }
  t << "BRIEF_MEMBER_DESC      = ";
  writeBoolValue(t,Config::briefMemDescFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the REPEAT_BRIEF tag is set to YES (the default) Doxygen will prepend \n";
    t << "# the brief description of a member or function before the detailed description. \n";
    t << "# Note: if both HIDE_UNDOC_MEMBERS and BRIEF_MEMBER_DESC are set to NO, the \n";
    t << "# brief descriptions will be completely suppressed. \n";
    t << "\n";
  }
  t << "REPEAT_BRIEF           = ";
  writeBoolValue(t,Config::repeatBriefFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the ALWAYS_DETAILED_SEC and REPEAT_BRIEF tags are both set to YES then \n";
    t << "# Doxygen will generate a detailed section even if there is only a brief \n";
    t << "# description. \n";
    t << "\n";
  }
  t << "ALWAYS_DETAILED_SEC    = ";
  writeBoolValue(t,Config::alwaysDetailsFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the FULL_PATH_NAMES tag is set to YES then Doxygen will prepend the full \n";
    t << "# path before files name in the file list and in the header files. If set \n";
    t << "# to NO the shortest path that makes the file name unique will be used. \n";
    t << "\n";
  }
  t << "FULL_PATH_NAMES        = ";
  writeBoolValue(t,Config::fullPathNameFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the FULL_PATH_NAMES tag is set to YES then the STRIP_FROM_PATH tag \n";
    t << "# can be used to strip a user defined part of the path. Stripping is \n";
    t << "# only done if one of the specified strings matches the left-hand part of \n";
    t << "# the path. It is allowed to use relative paths in the argument list.\n";
    t << "\n";
  }
  t << "STRIP_FROM_PATH        = ";
  writeStringList(t,Config::stripFromPath);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The INTERNAL_DOCS tag determines if documentation \n";
    t << "# that is typed after a \\internal command is included. If the tag is set \n";
    t << "# to NO (the default) then the documentation will be excluded. \n";
    t << "# Set it to YES to include the internal documentation. \n";
    t << "\n";
  }
  t << "INTERNAL_DOCS          = ";
  writeBoolValue(t,Config::internalDocsFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the CLASS_DIAGRAMS tag is set to YES (the default) Doxygen will \n";
    t << "# generate a class diagram (in Html and LaTeX) for classes with base or \n";
    t << "# super classes. Setting the tag to NO turns the diagrams off. \n";
    t << "\n";
  }
  t << "CLASS_DIAGRAMS         = ";
  writeBoolValue(t,Config::classDiagramFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the SOURCE_BROWSER tag is set to YES then a list of source files will \n";
    t << "# be generated. Documented entities will be cross-referenced with these sources. \n";
    t << "\n";
  }
  t << "SOURCE_BROWSER         = ";
  writeBoolValue(t,Config::sourceBrowseFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# Setting the INLINE_SOURCES tag to YES will include the body \n";
    t << "# of functions and classes directly in the documentation. \n";
    t << "\n";
  }
  t << "INLINE_SOURCES         = ";
  writeBoolValue(t,Config::inlineSourceFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# Setting the STRIP_CODE_COMMENTS tag to YES (the default) will instruct \n";
    t << "# doxygen to hide any special comment blocks from generated source code \n";
    t << "# fragments. Normal C and C++ comments will always remain visible. \n";
    t << "\n";
  }
  t << "STRIP_CODE_COMMENTS    = ";
  writeBoolValue(t,Config::stripCommentsFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the CASE_SENSE_NAMES tag is set to NO (the default) then Doxygen \n";
    t << "# will only generate file names in lower case letters. If set to \n";
    t << "# YES upper case letters are also allowed. This is useful if you have \n";
    t << "# classes or files whose names only differ in case and if your file system \n";
    t << "# supports case sensitive file names. \n";
    t << "\n";
  }
  t << "CASE_SENSE_NAMES       = ";
  writeBoolValue(t,Config::caseSensitiveNames);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the HIDE_SCOPE_NAMES tag is set to NO (the default) then Doxygen \n";
    t << "# will show members with their full class and namespace scopes in the \n";
    t << "# documentation. If set to YES the scope will be hidden. \n";
    t << "\n";
  }
  t << "HIDE_SCOPE_NAMES       = ";
  writeBoolValue(t,Config::hideScopeNames);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the VERBATIM_HEADERS tag is set to YES (the default) then Doxygen \n";
    t << "# will generate a verbatim copy of the header file for each class for \n";
    t << "# which an include is specified. Set to NO to disable this. \n";
    t << "\n";
  }
  t << "VERBATIM_HEADERS       = ";
  writeBoolValue(t,Config::verbatimHeaderFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the SHOW_INCLUDE_FILES tag is set to YES (the default) then Doxygen \n";
    t << "# will put list of the files that are included by a file in the documentation \n";
    t << "# of that file. \n";
    t << "\n";
  }
  t << "SHOW_INCLUDE_FILES     = ";
  writeBoolValue(t,Config::showIncFileFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the JAVADOC_AUTOBRIEF tag is set to YES (the default) then Doxygen \n";
    t << "# will interpret the first line (until the first dot) of a JavaDoc-style \n";
    t << "# comment as the brief description. If set to NO, the Javadoc-style will \n";
    t << "# behave just like the Qt-style comments. \n";
    t << "\n";
  }
  t << "JAVADOC_AUTOBRIEF      = ";
  writeBoolValue(t,Config::autoBriefFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the INHERIT_DOCS tag is set to YES (the default) then an undocumented \n";
    t << "# member inherits the documentation from any documented member that it \n";
    t << "# reimplements. \n";
    t << "\n";
  }
  t << "INHERIT_DOCS           = ";
  writeBoolValue(t,Config::inheritDocsFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the INLINE_INFO tag is set to YES (the default) then a tag [inline] \n";
    t << "# is inserted in the documentation for inline members. \n";
    t << "\n";
  }
  t << "INLINE_INFO            = ";
  writeBoolValue(t,Config::inlineInfoFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the SORT_MEMBER_DOCS tag is set to YES (the default) then doxygen \n";
    t << "# will sort the (detailed) documentation of file and class members \n";
    t << "# alphabetically by member name. If set to NO the members will appear in \n";
    t << "# declaration order. \n";
    t << "\n";
  }
  t << "SORT_MEMBER_DOCS       = ";
  writeBoolValue(t,Config::sortMembersFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The TAB_SIZE tag can be used to set the number of spaces in a tab. \n";
    t << "# Doxygen uses this value to replace tabs by spaces in code fragments. \n";
    t << "\n";
  }
  t << "TAB_SIZE               = ";
  writeIntValue(t,Config::tabSize);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The ENABLE_SECTIONS tag can be used to enable conditional \n";
    t << "# documentation sections, marked by \\if sectionname ... \\endif. \n";
    t << "\n";
  }
  t << "ENABLED_SECTIONS       = ";
  writeStringList(t,Config::sectionFilterList);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The GENERATE_TODOLIST tag can be used to enable (YES) or \n";
    t << "# disable (NO) the todo list. This list is created by putting \\todo \n";
    t << "# commands in the documentation.\n";
    t << "\n";
  }
  t << "GENERATE_TODOLIST      = ";
  writeBoolValue(t,Config::generateTodoList);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The GENERATE_TESTLIST tag can be used to enable (YES) or \n";
    t << "# disable (NO) the test list. This list is created by putting \\test \n";
    t << "# commands in the documentation.\n";
    t << "\n";
  }
  t << "GENERATE_TESTLIST      = ";
  writeBoolValue(t,Config::generateTestList);
  t << "\n";
  if (!sl)
  {
    t << "\n";
  }
  t << "#---------------------------------------------------------------------------\n";
  t << "# configuration options related to warning and progress messages\n";
  t << "#---------------------------------------------------------------------------\n";
  if (!sl)
  {
    t << "\n";
    t << "# The QUIET tag can be used to turn on/off the messages that are generated \n";
    t << "# by doxygen. Possible values are YES and NO. If left blank NO is used. \n";
    t << "\n";
  }
  t << "QUIET                  = ";
  writeBoolValue(t,Config::quietFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The WARNINGS tag can be used to turn on/off the warning messages that are \n";
    t << "# generated by doxygen. Possible values are YES and NO. If left blank \n";
    t << "# NO is used. \n";
    t << "\n";
  }
  t << "WARNINGS               = ";
  writeBoolValue(t,Config::warningFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If WARN_IF_UNDOCUMENTED is set to YES, then doxygen will generate warnings \n";
    t << "# for undocumented members. If EXTRACT_ALL is set to YES then this flag will \n";
    t << "# automatically be disabled. \n";
    t << "\n";
  }
  t << "WARN_IF_UNDOCUMENTED   = ";
  writeBoolValue(t,Config::warningUndocFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The WARN_FORMAT tag determines the format of the warning messages that \n";
    t << "# doxygen can produce. The string should contain the $file, $line, and $text \n";
    t << "# tags, which will be replaced by the file and line number from which the \n";
    t << "# warning originated and the warning text. \n";
    t << "\n";
  }
  t << "WARN_FORMAT            = ";
  writeStringValue(t,Config::warnFormat);
  t << "\n";
  if (!sl)
  {
    t << "\n";
  }
  t << "#---------------------------------------------------------------------------\n";
  t << "# configuration options related to the input files\n";
  t << "#---------------------------------------------------------------------------\n";
  if (!sl)
  {
    t << "\n";
    t << "# The INPUT tag can be used to specify the files and/or directories that contain \n";
    t << "# documented source files. You may enter file names like \"myfile.cpp\" or \n";
    t << "# directories like \"/usr/src/myproject\". Separate the files or directories \n";
    t << "# with spaces. \n";
    t << "\n";
  }
  t << "INPUT                  = ";
  writeStringList(t,Config::inputSources);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the value of the INPUT tag contains directories, you can use the \n";
    t << "# FILE_PATTERNS tag to specify one or more wildcard pattern (like *.cpp \n";
    t << "# and *.h) to filter out the source-files in the directories. If left \n";
    t << "# blank all files are included. \n";
    t << "\n";
  }
  t << "FILE_PATTERNS          = ";
  writeStringList(t,Config::filePatternList);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The RECURSIVE tag can be used to turn specify whether or not subdirectories \n";
    t << "# should be searched for input files as well. Possible values are YES and NO. \n";
    t << "# If left blank NO is used. \n";
    t << "\n";
  }
  t << "RECURSIVE              = ";
  writeBoolValue(t,Config::recursiveFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The EXCLUDE tag can be used to specify files and/or directories that should \n";
    t << "# excluded from the INPUT source files. This way you can easily exclude a \n";
    t << "# subdirectory from a directory tree whose root is specified with the INPUT tag. \n";
    t << "\n";
  }
  t << "EXCLUDE                = ";
  writeStringList(t,Config::excludeSources);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the value of the INPUT tag contains directories, you can use the \n";
    t << "# EXCLUDE_PATTERNS tag to specify one or more wildcard patterns to exclude \n";
    t << "# certain files from those directories. \n";
    t << "\n";
  }
  t << "EXCLUDE_PATTERNS       = ";
  writeStringList(t,Config::excludePatternList);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The EXAMPLE_PATH tag can be used to specify one or more files or \n";
    t << "# directories that contain example code fragments that are included (see \n";
    t << "# the \\include command). \n";
    t << "\n";
  }
  t << "EXAMPLE_PATH           = ";
  writeStringList(t,Config::examplePath);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the value of the EXAMPLE_PATH tag contains directories, you can use the \n";
    t << "# EXAMPLE_PATTERNS tag to specify one or more wildcard pattern (like *.cpp \n";
    t << "# and *.h) to filter out the source-files in the directories. If left \n";
    t << "# blank all files are included. \n";
    t << "\n";
  }
  t << "EXAMPLE_PATTERNS       = ";
  writeStringList(t,Config::examplePatternList);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The IMAGE_PATH tag can be used to specify one or more files or \n";
    t << "# directories that contain image that are included in the documentation (see \n";
    t << "# the \\image command). \n";
    t << "\n";
  }
  t << "IMAGE_PATH             = ";
  writeStringList(t,Config::imagePath);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The INPUT_FILTER tag can be used to specify a program that doxygen should \n";
    t << "# invoke to filter for each input file. Doxygen will invoke the filter program \n";
    t << "# by executing (via popen()) the command <filter> <input-file>, where <filter> \n";
    t << "# is the value of the INPUT_FILTER tag, and <input-file> is the name of an \n";
    t << "# input file. Doxygen will then use the output that the filter program writes \n";
    t << "# to standard output. \n";
    t << "\n";
  }
  t << "INPUT_FILTER           = ";
  writeStringValue(t,Config::inputFilter);
  t << "\n";
  if (!sl)
  {
    t << "\n";
  }
  t << "#---------------------------------------------------------------------------\n";
  t << "# configuration options related to the alphabetical class index\n";
  t << "#---------------------------------------------------------------------------\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the ALPHABETICAL_INDEX tag is set to YES, an alphabetical index \n";
    t << "# of all compounds will be generated. Enable this if the project \n";
    t << "# contains a lot of classes, structs, unions or interfaces. \n";
    t << "\n";
  }
  t << "ALPHABETICAL_INDEX     = ";
  writeBoolValue(t,Config::alphaIndexFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the alphabetical index is enabled (see ALPHABETICAL_INDEX) then \n";
    t << "# the COLS_IN_ALPHA_INDEX tag can be used to specify the number of columns \n";
    t << "# in which this list will be split (can be a number in the range [1..20]) \n";
    t << "\n";
  }
  t << "COLS_IN_ALPHA_INDEX    = ";
  writeIntValue(t,Config::colsInAlphaIndex);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# In case all classes in a project start with a common prefix, all \n";
    t << "# classes will be put under the same header in the alphabetical index. \n";
    t << "# The IGNORE_PREFIX tag can be used to specify one or more prefixes that \n";
    t << "# should be ignored while generating the index headers. \n";
    t << "\n";
  }
  t << "IGNORE_PREFIX          = ";
  writeStringList(t,Config::ignorePrefixList);
  t << "\n";
  if (!sl)
  {
    t << "\n";
  }
  t << "#---------------------------------------------------------------------------\n";
  t << "# configuration options related to the HTML output\n";
  t << "#---------------------------------------------------------------------------\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the GENERATE_HTML tag is set to YES (the default) Doxygen will \n";
    t << "# generate HTML output. \n";
    t << "\n";
  }
  t << "GENERATE_HTML          = ";
  writeBoolValue(t,Config::generateHtml);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The HTML_OUTPUT tag is used to specify where the HTML docs will be put. \n";
    t << "# If a relative path is entered the value of OUTPUT_DIRECTORY will be \n";
    t << "# put in front of it. If left blank `html' will be used as the default path. \n";
    t << "\n";
  }
  t << "HTML_OUTPUT            = ";
  writeStringValue(t,Config::htmlOutputDir);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The HTML_HEADER tag can be used to specify a personal HTML header for \n";
    t << "# each generated HTML page. If it is left blank doxygen will generate a \n";
    t << "# standard header.\n";
    t << "\n";
  }
  t << "HTML_HEADER            = ";
  writeStringValue(t,Config::headerFile);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The HTML_FOOTER tag can be used to specify a personal HTML footer for \n";
    t << "# each generated HTML page. If it is left blank doxygen will generate a \n";
    t << "# standard footer.\n";
    t << "\n";
  }
  t << "HTML_FOOTER            = ";
  writeStringValue(t,Config::footerFile);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The HTML_STYLESHEET tag can be used to specify a user defined cascading \n";
    t << "# style sheet that is used by each HTML page. It can be used to \n";
    t << "# fine-tune the look of the HTML output. If the tag is left blank doxygen \n";
    t << "# will generate a default style sheet \n";
    t << "\n";
  }
  t << "HTML_STYLESHEET        = ";
  writeStringValue(t,Config::htmlStyleSheet);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the HTML_ALIGN_MEMBERS tag is set to YES, the members of classes, \n";
    t << "# files or namespaces will be aligned in HTML using tables. If set to \n";
    t << "# NO a bullet list will be used. \n";
    t << "\n";
  }
  t << "HTML_ALIGN_MEMBERS     = ";
  writeBoolValue(t,Config::htmlAlignMemberFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the GENERATE_HTMLHELP tag is set to YES, additional index files \n";
    t << "# will be generated that can be used as input for tools like the \n";
    t << "# Microsoft HTML help workshop to generate a compressed HTML help file (.chm) \n";
    t << "# of the generated HTML documentation. \n";
    t << "\n";
  }
  t << "GENERATE_HTMLHELP      = ";
  writeBoolValue(t,Config::htmlHelpFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The DISABLE_INDEX tag can be used to turn on/off the condensed index at \n";
    t << "# top of each HTML page. The value NO (the default) enables the index and \n";
    t << "# the value YES disables it. \n";
    t << "\n";
  }
  t << "DISABLE_INDEX          = ";
  writeBoolValue(t,Config::noIndexFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
  }
  t << "#---------------------------------------------------------------------------\n";
  t << "# configuration options related to the LaTeX output\n";
  t << "#---------------------------------------------------------------------------\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the GENERATE_LATEX tag is set to YES (the default) Doxygen will \n";
    t << "# generate Latex output. \n";
    t << "\n";
  }
  t << "GENERATE_LATEX         = ";
  writeBoolValue(t,Config::generateLatex);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The LATEX_OUTPUT tag is used to specify where the LaTeX docs will be put. \n";
    t << "# If a relative path is entered the value of OUTPUT_DIRECTORY will be \n";
    t << "# put in front of it. If left blank `latex' will be used as the default path. \n";
    t << "\n";
  }
  t << "LATEX_OUTPUT           = ";
  writeStringValue(t,Config::latexOutputDir);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the COMPACT_LATEX tag is set to YES Doxygen generates more compact \n";
    t << "# LaTeX documents. This may be useful for small projects and may help to \n";
    t << "# save some trees in general. \n";
    t << "\n";
  }
  t << "COMPACT_LATEX          = ";
  writeBoolValue(t,Config::compactLatexFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The PAPER_TYPE tag can be used to set the paper type that is used \n";
    t << "# by the printer. Possible values are: a4, a4wide, letter, legal and \n";
    t << "# executive. If left blank a4wide will be used. \n";
    t << "\n";
  }
  t << "PAPER_TYPE             = ";
  writeStringValue(t,Config::paperType);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The EXTRA_PACKAGES tag can be to specify one or more names of LaTeX \n";
    t << "# packages that should be included in the LaTeX output. \n";
    t << "\n";
  }
  t << "EXTRA_PACKAGES         = ";
  writeStringList(t,Config::extraPackageList);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The LATEX_HEADER tag can be used to specify a personal LaTeX header for \n";
    t << "# the generated latex document. The header should contain everything until \n";
    t << "# the first chapter. If it is left blank doxygen will generate a \n";
    t << "# standard header. Notice: only use this tag if you know what you are doing! \n";
    t << "\n";
  }
  t << "LATEX_HEADER           = ";
  writeStringValue(t,Config::latexHeaderFile);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the PDF_HYPERLINKS tag is set to YES, the LaTeX that is generated \n";
    t << "# is prepared for conversion to pdf (using ps2pdf). The pdf file will \n";
    t << "# contain links (just like the HTML output) instead of page references \n";
    t << "# This makes the output suitable for online browsing using a pdf viewer. \n";
    t << "\n";
  }
  t << "PDF_HYPERLINKS         = ";
  writeBoolValue(t,Config::pdfHyperFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the USE_PDFLATEX tag is set to YES, pdflatex will be used instead of \n";
    t << "# plain latex in the generated Makefile. Set this option to YES to get a \n";
    t << "# higher quality PDF documentation. \n";
    t << "\n";
  }
  t << "USE_PDFLATEX           = ";
  writeBoolValue(t,Config::usePDFLatexFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the LATEX_BATCHMODE tag is set to YES, doxygen will add the \\\\batchmode. \n";
    t << "# command to the generated LaTeX files. This will instruct LaTeX to keep \n";
    t << "# running if errors occur, instead of asking the user for help. \n";
    t << "# This option is also used when generating formulas in HTML. \n";
    t << "\n";
  }
  t << "LATEX_BATCHMODE        = ";
  writeBoolValue(t,Config::latexBatchModeFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
  }
  t << "#---------------------------------------------------------------------------\n";
  t << "# configuration options related to the RTF output\n";
  t << "#---------------------------------------------------------------------------\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the GENERATE_RTF tag is set to YES Doxygen will generate RTF output \n";
    t << "# The RTF output is optimised for Word 97 and may not look very pretty with \n";
    t << "# other RTF readers or editors.\n";
    t << "\n";
  }
  t << "GENERATE_RTF           = ";
  writeBoolValue(t,Config::generateRTF);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The RTF_OUTPUT tag is used to specify where the RTF docs will be put. \n";
    t << "# If a relative path is entered the value of OUTPUT_DIRECTORY will be \n";
    t << "# put in front of it. If left blank `rtf' will be used as the default path. \n";
    t << "\n";
  }
  t << "RTF_OUTPUT             = ";
  writeStringValue(t,Config::rtfOutputDir);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the COMPACT_RTF tag is set to YES Doxygen generates more compact \n";
    t << "# RTF documents. This may be useful for small projects and may help to \n";
    t << "# save some trees in general. \n";
    t << "\n";
  }
  t << "COMPACT_RTF            = ";
  writeBoolValue(t,Config::compactRTFFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the RTF_HYPERLINKS tag is set to YES, the RTF that is generated \n";
    t << "# will contain hyperlink fields. The RTF file will \n";
    t << "# contain links (just like the HTML output) instead of page references. \n";
    t << "# This makes the output suitable for online browsing using a WORD or other. \n";
    t << "# programs which support those fields. \n";
    t << "# Note: wordpad (write) and others do not support links. \n";
    t << "\n";
  }
  t << "RTF_HYPERLINKS         = ";
  writeBoolValue(t,Config::rtfHyperFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# Load stylesheet definitions from file. Syntax is similar to doxygen's \n";
    t << "# config file, i.e. a series of assigments. You only have to provide \n";
    t << "# replacements, missing definitions are set to their default value. \n";
    t << "\n";
  }
  t << "RTF_STYLESHEET_FILE    = ";
  writeStringValue(t,Config::rtfStylesheetFile);
  t << "\n";
  if (!sl)
  {
    t << "\n";
  }
  t << "#---------------------------------------------------------------------------\n";
  t << "# configuration options related to the man page output\n";
  t << "#---------------------------------------------------------------------------\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the GENERATE_MAN tag is set to YES (the default) Doxygen will \n";
    t << "# generate man pages \n";
    t << "\n";
  }
  t << "GENERATE_MAN           = ";
  writeBoolValue(t,Config::generateMan);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The MAN_OUTPUT tag is used to specify where the man pages will be put. \n";
    t << "# If a relative path is entered the value of OUTPUT_DIRECTORY will be \n";
    t << "# put in front of it. If left blank `man' will be used as the default path. \n";
    t << "\n";
  }
  t << "MAN_OUTPUT             = ";
  writeStringValue(t,Config::manOutputDir);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The MAN_EXTENSION tag determines the extension that is added to \n";
    t << "# the generated man pages (default is the subroutine's section .3) \n";
    t << "\n";
  }
  t << "MAN_EXTENSION          = ";
  writeStringValue(t,Config::manExtension);
  t << "\n";
  if (!sl)
  {
    t << "\n";
  }
  t << "#---------------------------------------------------------------------------\n";
  t << "# configuration options related to the XML output\n";
  t << "#---------------------------------------------------------------------------\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the GENERATE_XML tag is set to YES Doxygen will \n";
    t << "# generate an XML file that captures the structure of \n";
    t << "# the code including all documentation. Warning: This feature \n";
    t << "# is still experimental and very incomplete.\n";
    t << "\n";
  }
  t << "GENERATE_XML           = ";
  writeBoolValue(t,Config::generateXML);
  t << "\n";
  if (!sl)
  {
    t << "\n";
  }
  t << "#---------------------------------------------------------------------------\n";
  t << "# Configuration options related to the preprocessor   \n";
  t << "#---------------------------------------------------------------------------\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the ENABLE_PREPROCESSING tag is set to YES (the default) Doxygen will \n";
    t << "# evaluate all C-preprocessor directives found in the sources and include \n";
    t << "# files. \n";
    t << "\n";
  }
  t << "ENABLE_PREPROCESSING   = ";
  writeBoolValue(t,Config::preprocessingFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the MACRO_EXPANSION tag is set to YES Doxygen will expand all macro \n";
    t << "# names in the source code. If set to NO (the default) only conditional \n";
    t << "# compilation will be performed. Macro expansion can be done in a controlled \n";
    t << "# way by setting EXPAND_ONLY_PREDEF to YES. \n";
    t << "\n";
  }
  t << "MACRO_EXPANSION        = ";
  writeBoolValue(t,Config::macroExpansionFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the EXPAND_ONLY_PREDEF and MACRO_EXPANSION tags are both set to YES \n";
    t << "# then the macro expansion is limited to the macros specified with the \n";
    t << "# PREDEFINED and EXPAND_AS_PREDEFINED tags. \n";
    t << "\n";
  }
  t << "EXPAND_ONLY_PREDEF     = ";
  writeBoolValue(t,Config::onlyPredefinedFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the SEARCH_INCLUDES tag is set to YES (the default) the includes files \n";
    t << "# in the INCLUDE_PATH (see below) will be search if a #include is found. \n";
    t << "\n";
  }
  t << "SEARCH_INCLUDES        = ";
  writeBoolValue(t,Config::searchIncludeFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The INCLUDE_PATH tag can be used to specify one or more directories that \n";
    t << "# contain include files that are not input files but should be processed by \n";
    t << "# the preprocessor. \n";
    t << "\n";
  }
  t << "INCLUDE_PATH           = ";
  writeStringList(t,Config::includePath);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# You can use the INCLUDE_FILE_PATTERNS tag to specify one or more wildcard \n";
    t << "# patterns (like *.h and *.hpp) to filter out the header-files in the \n";
    t << "# directories. If left blank, the patterns specified with FILE_PATTERNS will \n";
    t << "# be used. \n";
    t << "\n";
  }
  t << "INCLUDE_FILE_PATTERNS  = ";
  writeStringList(t,Config::includeFilePatternList);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The PREDEFINED tag can be used to specify one or more macro names that \n";
    t << "# are defined before the preprocessor is started (similar to the -D option of \n";
    t << "# gcc). The argument of the tag is a list of macros of the form: name \n";
    t << "# or name=definition (no spaces). If the definition and the = are \n";
    t << "# omitted =1 is assumed. \n";
    t << "\n";
  }
  t << "PREDEFINED             = ";
  writeStringList(t,Config::predefined);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the MACRO_EXPANSION and EXPAND_PREDEF_ONLY tags are set to YES then \n";
    t << "# this tag can be used to specify a list of macro names that should be expanded. \n";
    t << "# The macro definition that is found in the sources will be used. \n";
    t << "# Use the PREDEFINED tag if you want to use a different macro definition. \n";
    t << "\n";
  }
  t << "EXPAND_AS_DEFINED      = ";
  writeStringList(t,Config::expandAsDefinedList);
  t << "\n";
  if (!sl)
  {
    t << "\n";
  }
  t << "#---------------------------------------------------------------------------\n";
  t << "# Configuration::addtions related to external references   \n";
  t << "#---------------------------------------------------------------------------\n";
  if (!sl)
  {
    t << "\n";
    t << "# The TAGFILES tag can be used to specify one or more tagfiles. \n";
    t << "\n";
  }
  t << "TAGFILES               = ";
  writeStringList(t,Config::tagFileList);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# When a file name is specified after GENERATE_TAGFILE, doxygen will create \n";
    t << "# a tag file that is based on the input files it reads. \n";
    t << "\n";
  }
  t << "GENERATE_TAGFILE       = ";
  writeStringValue(t,Config::genTagFile);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the ALLEXTERNALS tag is set to YES all external classes will be listed \n";
    t << "# in the class index. If set to NO only the inherited external classes \n";
    t << "# will be listed. \n";
    t << "\n";
  }
  t << "ALLEXTERNALS           = ";
  writeBoolValue(t,Config::allExtFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The PERL_PATH should be the absolute path and name of the perl script \n";
    t << "# interpreter (i.e. the result of `which perl'). \n";
    t << "\n";
  }
  t << "PERL_PATH              = ";
  writeStringValue(t,Config::perlPath);
  t << "\n";
  if (!sl)
  {
    t << "\n";
  }
  t << "#---------------------------------------------------------------------------\n";
  t << "# Configuration options related to the dot tool   \n";
  t << "#---------------------------------------------------------------------------\n";
  if (!sl)
  {
    t << "\n";
    t << "# If you set the HAVE_DOT tag to YES then doxygen will assume the dot tool is \n";
    t << "# available from the path. This tool is part of Graphviz, a graph visualization \n";
    t << "# toolkit from AT&T and Lucent Bell Labs. The other options in this section \n";
    t << "# have no effect if this option is set to NO (the default) \n";
    t << "\n";
  }
  t << "HAVE_DOT               = ";
  writeBoolValue(t,Config::haveDotFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the CLASS_GRAPH and HAVE_DOT tags are set to YES then doxygen \n";
    t << "# will generate a graph for each documented class showing the direct and \n";
    t << "# indirect inheritance relations. Setting this tag to YES will force the \n";
    t << "# the CLASS_DIAGRAMS tag to NO.\n";
    t << "\n";
  }
  t << "CLASS_GRAPH            = ";
  writeBoolValue(t,Config::classGraphFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the COLLABORATION_GRAPH and HAVE_DOT tags are set to YES then doxygen \n";
    t << "# will generate a graph for each documented class showing the direct and \n";
    t << "# indirect implementation dependencies (inheritance, containment, and \n";
    t << "# class references variables) of the class with other documented classes. \n";
    t << "\n";
  }
  t << "COLLABORATION_GRAPH    = ";
  writeBoolValue(t,Config::collGraphFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the ENABLE_PREPROCESSING, INCLUDE_GRAPH, and HAVE_DOT tags are set to \n";
    t << "# YES then doxygen will generate a graph for each documented file showing \n";
    t << "# the direct and indirect include dependencies of the file with other \n";
    t << "# documented files. \n";
    t << "\n";
  }
  t << "INCLUDE_GRAPH          = ";
  writeBoolValue(t,Config::includeGraphFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the ENABLE_PREPROCESSING, INCLUDED_BY_GRAPH, and HAVE_DOT tags are set to \n";
    t << "# YES then doxygen will generate a graph for each documented header file showing \n";
    t << "# the documented files that directly or indirectly include this file \n";
    t << "\n";
  }
  t << "INCLUDED_BY_GRAPH      = ";
  writeBoolValue(t,Config::includedByGraphFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# If the GRAPHICAL_HIERARCHY and HAVE_DOT tags are set to YES then doxygen \n";
    t << "# will graphical hierarchy of all classes instead of a textual one. \n";
    t << "\n";
  }
  t << "GRAPHICAL_HIERARCHY    = ";
  writeBoolValue(t,Config::gfxHierarchyFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The tag DOT_PATH can be used to specify the path where the dot tool can be \n";
    t << "# found. If left blank, it is assumed the dot tool can be found on the path. \n";
    t << "\n";
  }
  t << "DOT_PATH               = ";
  writeStringValue(t,Config::dotPath);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The MAX_DOT_GRAPH_WIDTH tag can be used to set the maximum allowed width \n";
    t << "# (in pixels) of the graphs generated by dot. If a graph becomes larger than \n";
    t << "# this value, doxygen will try to truncate the graph, so that it fits within \n";
    t << "# the specified constraint. Beware that most browsers cannot cope with very \n";
    t << "# large images. \n";
    t << "\n";
  }
  t << "MAX_DOT_GRAPH_WIDTH    = ";
  writeIntValue(t,Config::maxDotGraphWidth);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The MAX_DOT_GRAPH_HEIGHT tag can be used to set the maximum allows height \n";
    t << "# (in pixels) of the graphs generated by dot. If a graph becomes larger than \n";
    t << "# this value, doxygen will try to truncate the graph, so that it fits within \n";
    t << "# the specified constraint. Beware that most browsers cannot cope with very \n";
    t << "# large images. \n";
    t << "\n";
  }
  t << "MAX_DOT_GRAPH_HEIGHT   = ";
  writeIntValue(t,Config::maxDotGraphHeight);
  t << "\n";
  if (!sl)
  {
    t << "\n";
  }
  t << "#---------------------------------------------------------------------------\n";
  t << "# Configuration::addtions related to the search engine   \n";
  t << "#---------------------------------------------------------------------------\n";
  if (!sl)
  {
    t << "\n";
    t << "# The SEARCHENGINE tag specifies whether or not a search engine should be \n";
    t << "# used. If set to NO the values of all tags below this one will be ignored. \n";
    t << "\n";
  }
  t << "SEARCHENGINE           = ";
  writeBoolValue(t,Config::searchEngineFlag);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The CGI_NAME tag should be the name of the CGI script that \n";
    t << "# starts the search engine (doxysearch) with the correct parameters. \n";
    t << "# A script with this name will be generated by doxygen. \n";
    t << "\n";
  }
  t << "CGI_NAME               = ";
  writeStringValue(t,Config::cgiName);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The CGI_URL tag should be the absolute URL to the directory where the \n";
    t << "# cgi binaries are located. See the documentation of your http daemon for \n";
    t << "# details. \n";
    t << "\n";
  }
  t << "CGI_URL                = ";
  writeStringValue(t,Config::cgiURL);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The DOC_URL tag should be the absolute URL to the directory where the \n";
    t << "# documentation is located. If left blank the absolute path to the \n";
    t << "# documentation, with file:// prepended to it, will be used. \n";
    t << "\n";
  }
  t << "DOC_URL                = ";
  writeStringValue(t,Config::docURL);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The DOC_ABSPATH tag should be the absolute path to the directory where the \n";
    t << "# documentation is located. If left blank the directory on the local machine \n";
    t << "# will be used. \n";
    t << "\n";
  }
  t << "DOC_ABSPATH            = ";
  writeStringValue(t,Config::docAbsPath);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The BIN_ABSPATH tag must point to the directory where the doxysearch binary \n";
    t << "# is installed. \n";
    t << "\n";
  }
  t << "BIN_ABSPATH            = ";
  writeStringValue(t,Config::binAbsPath);
  t << "\n";
  if (!sl)
  {
    t << "\n";
    t << "# The EXT_DOC_PATHS tag can be used to specify one or more paths to \n";
    t << "# documentation generated for other projects. This allows doxysearch to search \n";
    t << "# the documentation for these projects as well. \n";
    t << "\n";
  }
  t << "EXT_DOC_PATHS          = ";
  writeStringList(t,Config::extDocPathList);
  t << "\n";
}

void configStrToVal()
{
  if (tabSizeString.isEmpty())
  {
    Config::tabSize=8;
  }
  else
  {
    bool ok;
    int ts = tabSizeString.toInt(&ok);
    if (!ok || ts<1 || ts>16)
    {
      warn_cont("Warning: argument of TAB_SIZE is not a valid number, using tab size of 8 spaces!\n");
      ts=8;
    }
    Config::tabSize = ts;
  }
  
  if (colsInAlphaIndexString.isEmpty())
  {
    Config::colsInAlphaIndex=5;
  }
  else
  {
    bool ok;
    int cols = colsInAlphaIndexString.toInt(&ok);
    if (!ok || cols<1 || cols>20)
    {
      warn_cont("Warning: argument of COLS_IN_ALPHA_INDEX is not a valid number in the range [1..20]!\n"
	   "Using the default of 5 columns!\n");
      cols = 5;
    }
    Config::colsInAlphaIndex=cols;
  }
  
  if (maxDotGraphWidthString.isEmpty())
  {
    Config::maxDotGraphWidth=1024;
  }
  else
  {
    bool ok;
    int width =maxDotGraphWidthString.toInt(&ok);
    if (!ok)
    {
      warn_cont("Warning: argument of MAX_DOT_GRAPH_WIDTH is not a valid number in the range [1..20]!\n"
	   "Using the default of 1024 pixels!\n");
      width=1024;
    }
    else if (width<100) // clip to lower bound
    {
      width=100;
    }
    else if (width>30000) // clip to upper bound
    {
      width=30000;
    }
    Config::maxDotGraphWidth=width;
  }

  if (maxDotGraphHeightString.isEmpty())
  {
    Config::maxDotGraphHeight=1024;
  }
  else
  {
    bool ok;
    int height =maxDotGraphHeightString.toInt(&ok);
    if (!ok)
    {
      warn_cont("Warning: argument of MAX_DOT_GRAPH_WIDTH is not a valid number in the range [1..20]!\n"
	   "Using the default of 1024 pixels!\n");
      height=1024;
    }
    else if (height<100) // clip to lower bound
    {
      height=100;
    }
    else if (height>30000) // clip to upper bound
    {
      height=30000;
    }
    Config::maxDotGraphHeight=height;
  }
}

static void substEnvVarsInString(QCString &s)
{
  static QRegExp re("\\$\\([a-z_A-Z0-9]+\\)");
  if (s.isEmpty()) return;
  int p=0;
  int i,l;
  //printf("substEnvVarInString(%s) start\n",s.data());
  while ((i=re.match(s,p,&l))!=-1)
  {
    //printf("Found environment var s.mid(%d,%d)=`%s'\n",i+2,l-3,s.mid(i+2,l-3).data());
    QCString env=getenv(s.mid(i+2,l-3));
    substEnvVarsInString(env); // recursively expand variables if needed.
    s = s.left(i)+env+s.right(s.length()-i-l);
    p=i+env.length(); // next time start at the end of the expanded string
  }
  //printf("substEnvVarInString(%s) end\n",s.data());
}

static void substEnvVarsInStrList(QStrList &sl)
{
  char *s = sl.first();
  while (s)
  {
    QCString result(s);
    bool wasQuoted = (result.find(' ')!=-1) || (result.find('\t')!=-1);
    substEnvVarsInString(result);

    if (!wasQuoted) /* as a result of the expansion, a single string
		       may have expanded into a list, which we'll
		       add to sl. If the orginal string already 
		       contained multiple elements no further 
		       splitting is done to allow quoted items with spaces! */
    {



      int l=result.length();
      int i,p=0;
      // skip spaces
      // search for a "word"
      for (i=0;i<l;i++)
      {
	char c;
	// skip until start of new word
	while (i<l && ((c=result.at(i))==' ' || c=='\t')) i++; 
	p=i; // p marks the start index of the word
	// skip until end of a word
	while (i<l && ((c=result.at(i))!=' ' && c!='\t' && c!='"')) i++;
	if (i<l) // not at the end of the string
	{
	  if (c=='"') // word within quotes
	  {
	    p=i+1;
	    for (i++;i<l;i++)
	    {
	      c=result.at(i);
	      if (c=='"') // end quote
	      {
		// replace the string in the list and go to the next item.
		sl.insert(sl.at(),result.mid(p,i-p)); // insert new item before current item.
		sl.next();                 // current item is now the old item
		p=i+1;
		break; 
	      }
	      else if (c=='\\') // skip escaped stuff
	      {
		i++;
	      }
	    }
	  }
	  else if (c==' ' || c=='\t') // separator
	  {
	    // replace the string in the list and go to the next item.
	    sl.insert(sl.at(),result.mid(p,i-p)); // insert new item before current item.
	    sl.next();                 // current item is now the old item
	    p=i+1;
	  }
	}
      }
      if (p!=l) // add the leftover as a string
      {
	// replace the string in the list and go to the next item.
	sl.insert(sl.at(),result.right(l-p)); // insert new item before current item.
	sl.next();                 // current item is now the old item
      }

      // remove the old unexpanded string from the list
      i=sl.at();
      sl.remove(); // current item index changes if the last element is removed.
      if (sl.at()==i)     // not last item
	s = sl.current();
      else                // just removed last item
	s = 0;
    }
    else // just goto the next element in the list
    {
      s=sl.next();
    }
  }
}


void substituteEnvironmentVars()
{
  substEnvVarsInString( Config::projectName );
  substEnvVarsInString( Config::projectNumber );
  substEnvVarsInString( Config::outputDir );
  substEnvVarsInString( Config::outputLanguage );
  substEnvVarsInStrList( Config::stripFromPath );
  substEnvVarsInStrList( Config::sectionFilterList );
  substEnvVarsInString( Config::warnFormat );
  substEnvVarsInStrList( Config::inputSources );
  substEnvVarsInStrList( Config::filePatternList );
  substEnvVarsInStrList( Config::excludeSources );
  substEnvVarsInStrList( Config::excludePatternList );
  substEnvVarsInStrList( Config::examplePath );
  substEnvVarsInStrList( Config::examplePatternList );
  substEnvVarsInStrList( Config::imagePath );
  substEnvVarsInString( Config::inputFilter );
  substEnvVarsInStrList( Config::ignorePrefixList );
  substEnvVarsInString( Config::htmlOutputDir );
  substEnvVarsInString( Config::headerFile );
  substEnvVarsInString( Config::footerFile );
  substEnvVarsInString( Config::htmlStyleSheet );
  substEnvVarsInString( Config::latexOutputDir );
  substEnvVarsInString( Config::paperType );
  substEnvVarsInStrList( Config::extraPackageList );
  substEnvVarsInString( Config::latexHeaderFile );
  substEnvVarsInString( Config::rtfOutputDir );
  substEnvVarsInString( Config::rtfStylesheetFile );
  substEnvVarsInString( Config::manOutputDir );
  substEnvVarsInString( Config::manExtension );
  substEnvVarsInStrList( Config::includePath );
  substEnvVarsInStrList( Config::includeFilePatternList );
  substEnvVarsInStrList( Config::predefined );
  substEnvVarsInStrList( Config::expandAsDefinedList );
  substEnvVarsInStrList( Config::tagFileList );
  substEnvVarsInString( Config::genTagFile );
  substEnvVarsInString( Config::perlPath );
  substEnvVarsInString( Config::dotPath );
  substEnvVarsInString( Config::cgiName );
  substEnvVarsInString( Config::cgiURL );
  substEnvVarsInString( Config::docURL );
  substEnvVarsInString( Config::docAbsPath );
  substEnvVarsInString( Config::binAbsPath );
  substEnvVarsInStrList( Config::extDocPathList );
}

void checkConfig()
{
  //if (!projectName.isEmpty())
  //{
  //  projectName[0]=toupper(projectName[0]);
  //}

  if (Config::warnFormat.isEmpty())
  {
    Config::warnFormat="$file:$line $text";
  }
  else
  {
    if (Config::warnFormat.find("$file")==-1)
    {
      err("Error: warning format does not contain a $file tag!\n");
      exit(1);
    }
    if (Config::warnFormat.find("$line")==-1)
    {
      err("Error: warning format does not contain a $line tag!\n");
      exit(1);
    }
    if (Config::warnFormat.find("$text")==-1)
    {
      err("Error: wanring format foes not contain a $text tag!\n");
      exit(1);
    }
  }
  initWarningFormat();

  // set default man page extension if non is given by the user
  if (Config::manExtension.isEmpty())
  {
    Config::manExtension=".3";
  }
  
  Config::paperType = Config::paperType.lower().stripWhiteSpace(); 
  if (Config::paperType.isEmpty())
  {
    Config::paperType = "a4wide";
  }
  if (Config::paperType!="a4" && Config::paperType!="a4wide" && Config::paperType!="letter" && 
      Config::paperType!="legal" && Config::paperType!="executive")
  {
    err("Error: Unknown page type specified");
  }
  
  Config::outputLanguage=Config::outputLanguage.stripWhiteSpace();
  if (Config::outputLanguage.isEmpty())
  {
    Config::outputLanguage = "English";
#ifndef DOXYWIZARD
    setTranslator("English");
#endif
  }
  else
  {
#ifndef DOXYWIZARD
    if (!setTranslator(Config::outputLanguage))
    {
      err("Error: Output language %s not supported! Using English instead.\n",
	  Config::outputLanguage.data());
    }
#endif
  }
  
  // Test to see if output directory is valid
  if (Config::outputDir.isEmpty()) 
    Config::outputDir=QDir::currentDirPath();
  else
  {
    QDir dir(Config::outputDir);
    if (!dir.exists())
    {
      dir.setPath(QDir::currentDirPath());
      if (!dir.mkdir(Config::outputDir))
      {
        err("Error: tag OUTPUT_DIRECTORY: Output directory `%s' does not "
	    "exist and cannot be created\n",Config::outputDir.data());
        exit(1);
      }
      else if (!Config::quietFlag)
      {
	err("Notice: Output directory `%s' does not exist. "
	    "I have created it for you.\n", Config::outputDir.data());
      }
      dir.cd(Config::outputDir);
    }
    Config::outputDir=dir.absPath();
  }

  if (Config::htmlOutputDir.isEmpty() && Config::generateHtml)
  {
    Config::htmlOutputDir=Config::outputDir+"/html";
  }
  else if (Config::htmlOutputDir && Config::htmlOutputDir[0]!='/')
  {
    Config::htmlOutputDir.prepend(Config::outputDir+'/');
  }
  QDir htmlDir(Config::htmlOutputDir);
  if (Config::generateHtml && !htmlDir.exists() && 
      !htmlDir.mkdir(Config::htmlOutputDir))
  {
    err("Could not create output directory %s\n",Config::htmlOutputDir.data());
    exit(1);
  }
  
  if (Config::latexOutputDir.isEmpty() && Config::generateLatex)
  {
    Config::latexOutputDir=Config::outputDir+"/latex";
  }
  else if (Config::latexOutputDir && Config::latexOutputDir[0]!='/')
  {
    Config::latexOutputDir.prepend(Config::outputDir+'/');
  }
  QDir latexDir(Config::latexOutputDir);
  if (Config::generateLatex && !latexDir.exists() && 
      !latexDir.mkdir(Config::latexOutputDir))
  {
    err("Could not create output directory %s\n",Config::latexOutputDir.data());
    exit(1);
  }
  
  if (Config::rtfOutputDir.isEmpty() && Config::generateRTF)
  {
    Config::rtfOutputDir=Config::outputDir+"/rtf";
  }
  else if (Config::rtfOutputDir && Config::rtfOutputDir[0]!='/')
  {
    Config::rtfOutputDir.prepend(Config::outputDir+'/');
  }
  QDir rtfDir(Config::rtfOutputDir);
  if (Config::generateRTF && !rtfDir.exists() && 
      !rtfDir.mkdir(Config::rtfOutputDir))
  {
    err("Could not create output directory %s\n",Config::rtfOutputDir.data());
    exit(1);
  }

  if (Config::manOutputDir.isEmpty() && Config::generateMan)
  {
    Config::manOutputDir=Config::outputDir+"/man";
  }
  else if (Config::manOutputDir && Config::manOutputDir[0]!='/')
  {
    Config::manOutputDir.prepend(Config::outputDir+'/');
  }
  QDir manDir(Config::manOutputDir);
  if (Config::generateMan && !manDir.exists() && 
      !manDir.mkdir(Config::manOutputDir))
  {
    err("Could not create output directory %s\n",Config::manOutputDir.data());
    exit(1);
  }

  // expand the relative stripFromPath values
  char *sfp = Config::stripFromPath.first();
  while (sfp)
  {
    QCString path = sfp;
    if (path.at(0)!='/' && (path.length()<=2 || path.at(1)!=':'))
    {
      QFileInfo fi(path);
      if (fi.exists() && fi.isDir())
      {
	int i = Config::stripFromPath.at();
	Config::stripFromPath.remove();
	if (Config::stripFromPath.at()==i) // did not remove last item
	  Config::stripFromPath.insert(i,fi.absFilePath()+"/");
	else
	  Config::stripFromPath.append(fi.absFilePath()+"/");
      }
    }
    sfp = Config::stripFromPath.next();
  }
  
  
  // Test to see if HTML header is valid
  if (!Config::headerFile.isEmpty())
  {
    QFileInfo fi(Config::headerFile);
    if (!fi.exists())
    {
      err("Error: tag HTML_HEADER: header file `%s' "
	  "does not exist\n",Config::headerFile.data());
      exit(1);
    }
  }
  // Test to see if HTML footer is valid
  if (!Config::footerFile.isEmpty())
  {
    QFileInfo fi(Config::footerFile);
    if (!fi.exists())
    {
      err("Error: tag HTML_FOOTER: footer file `%s' "
	  "does not exist\n",Config::footerFile.data());
      exit(1);
    }
  }
  // Test to see if LaTeX header is valid
  if (!Config::latexHeaderFile.isEmpty())
  {
    QFileInfo fi(Config::latexHeaderFile);
    if (!fi.exists())
    {
      err("Error: tag LATEX_HEADER: header file `%s' "
	  "does not exist\n",Config::latexHeaderFile.data());
      exit(1);
    }
  }
  // check include path
  char *s=Config::includePath.first();
  while (s)
  {
    QFileInfo fi(s);
    if (!fi.exists()) err("Warning: tag INCLUDE_PATH: include path `%s' "
	                  "does not exist\n",s);
#ifndef DOXYWIZARD
    addSearchDir(fi.absFilePath());
#endif
    s=Config::includePath.next();
  }
  
  // check dot path
  if (!Config::dotPath.isEmpty())
  {
    if (Config::dotPath.find('\\')!=-1)
    {
      if (Config::dotPath.at(Config::dotPath.length()-1)!='\\')
      {
	Config::dotPath+='\\';
      } 
    } 
    else if (Config::dotPath.find('/')!=-1)
    {
      if (Config::dotPath.at(Config::dotPath.length()-1)!='/')
      {
	Config::dotPath+='/';
      } 
    } 
#if defined(_WIN32)
    QFileInfo dp(Config::dotPath+"dot.exe");
#else
    QFileInfo dp(Config::dotPath+"dot");
#endif
    if (!dp.exists() || !dp.isFile())
    {
      err("Warning: the dot tool could not be found at %s\n",Config::dotPath.data());
    }
  }
  else // make sure the string is empty but not null!
  {
    Config::dotPath="";
  }
  
  // check input
  if (Config::inputSources.count()==0)
  {
    err("Error: tag INPUT: no input files specified after the INPUT tag.\n");
    exit(1);
  }
  else
  {
    s=Config::inputSources.first();
    while (s)
    {
      QFileInfo fi(s);
      if (!fi.exists())
      {
	err("Error: tag INPUT: input source `%s' does not exist\n",s);
	exit(1);
      }
      s=Config::inputSources.next();
    }
  }

  // add default pattern if needed
  if (Config::filePatternList.isEmpty())
  {
    Config::filePatternList.append("*");
  }

  // add default pattern if needed
  if (Config::examplePatternList.isEmpty())
  {
    Config::examplePatternList.append("*");
  }

  // add default pattern if needed
  //if (Config::imagePatternList.isEmpty())
  //{
  //  Config::imagePatternList.append("*");
  //}
  
  // more checks needed if and only if the search engine is enabled.
  if (Config::searchEngineFlag)
  {
    // check cgi name
    if (Config::cgiName.isEmpty())
    {
      err("Error: tag CGI_NAME: no cgi script name after the CGI_NAME tag.\n");
      exit(1);
    }
    // check cgi URL
    if (Config::cgiURL.isEmpty())
    {
      err("Error: tag CGI_URL: no URL to cgi directory specified.\n");
      exit(1);
    }
    else if (Config::cgiURL.left(7)!="http://" && 
	     Config::cgiURL.left(8)!="https://"
	    )
    {
      err("Error: tag CGI_URL: URL to cgi directory is invalid (must "
	  "start with http:// or https://).\n");
      exit(1);
    }
    // check documentation URL
    if (Config::docURL.isEmpty())
    {
      Config::docURL = Config::outputDir.copy().prepend("file://").append("html");
    }
    else if (Config::docURL.left(7)!="http://" && 
	     Config::docURL.left(8)!="https://" &&
	     Config::docURL.left(7)!="file://"
	    )
    {
      err("Error: tag DOC_URL: URL to documentation is invalid or "
	  "not absolute.\n"); 
      exit(1);
    }
    // check absolute documentation path
    if (Config::docAbsPath.isEmpty())
    {
      Config::docAbsPath = Config::outputDir+"/html"; 
    }
    else if (Config::docAbsPath[0]!='/' && Config::docAbsPath[1]!=':')
    {
      err("Error: tag DOC_ABSPATH: path is not absolute!\n");
      exit(1);
    }
    // check path to doxysearch
    if (Config::binAbsPath.isEmpty())
    {
      err("Error: tag BIN_ABSPATH: no absolute path to doxysearch "
	  "specified.\n");
      exit(1);
    }
    else if (Config::binAbsPath[0]!='/' && Config::binAbsPath[1]!=':')
    {
      err("Error: tag BIN_ABSPATH: path is not absolute!\n");
      exit(1);
    }

    // check perl path
    bool found=FALSE;
    if (Config::perlPath.isEmpty())
    {
      QFileInfo fi;
      fi.setFile("/usr/bin/perl");
      if (fi.exists()) 
      {
	Config::perlPath="/usr/bin/perl";
        found=TRUE;
      }
      else
      {
	fi.setFile("/usr/local/bin/perl");
	if (fi.exists())
        {
  	  Config::perlPath="/usr/local/bin/perl";
          found=TRUE;
        }
      }
    }
    if (!found)
    {
      QFileInfo fi(Config::perlPath);
      if (!fi.exists())
      {
        warn_cont("Warning: tag PERL_PATH: perl interpreter not found at default or"
            "user specified (%s) location\n",
        Config::perlPath.data());
      }
    }
  }

#if defined(_WIN32)
  if (Config::haveDotFlag) _putenv("DOTFONTPATH=.");
#endif
  
}

void parseConfig(const QCString &s,const char *fn)
{
  inputString   = s;
  inputPosition = 0;
  yyLineNr      = 1;
  yyFileName=fn;
  includeStack.setAutoDelete(TRUE);
  includeStack.clear();
  includeDepth  = 0;
  configYYrestart( configYYin );
  BEGIN( Start );
  configYYlex();
}

//extern "C" { // some bogus code to keep the compiler happy
//  int  configYYwrap() { return 1 ; }
//}
