Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
D
doxverilog
Project
Project
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Commits
Open sidebar
Elphel
doxverilog
Commits
05930245
Commit
05930245
authored
Nov 14, 2004
by
Dimitri van Heesch
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Release-1.3.9.1-20041114
parent
62d6edc6
Changes
39
Show whitespace changes
Inline
Side-by-side
Showing
39 changed files
with
1208 additions
and
263 deletions
+1208
-263
INSTALL
INSTALL
+2
-2
README
README
+2
-2
VERSION
VERSION
+1
-1
commands.doc
doc/commands.doc
+78
-1
config.doc
doc/config.doc
+12
-2
faq.doc
doc/faq.doc
+11
-2
infoflow.gif
doc/infoflow.gif
+0
-0
install.doc
doc/install.doc
+60
-56
language.doc
doc/language.doc
+3
-3
preprocessing.doc
doc/preprocessing.doc
+24
-2
translator_report.txt
doc/translator_report.txt
+3
-19
doxygen.spec
packages/rpm/doxygen.spec
+1
-1
commentcnv.h
src/commentcnv.h
+2
-1
commentcnv.l
src/commentcnv.l
+179
-28
config.l
src/config.l
+9
-0
debug.cpp
src/debug.cpp
+2
-0
debug.h
src/debug.h
+2
-1
dirdef.cpp
src/dirdef.cpp
+186
-30
dirdef.h
src/dirdef.h
+46
-6
docparser.cpp
src/docparser.cpp
+2
-2
dot.cpp
src/dot.cpp
+165
-29
dot.h
src/dot.h
+8
-0
doxygen.cpp
src/doxygen.cpp
+135
-60
doxygen.h
src/doxygen.h
+1
-0
htmlgen.cpp
src/htmlgen.cpp
+17
-0
htmlgen.h
src/htmlgen.h
+2
-0
htmlhelp.cpp
src/htmlhelp.cpp
+25
-3
latexgen.cpp
src/latexgen.cpp
+9
-0
latexgen.h
src/latexgen.h
+2
-0
mangen.h
src/mangen.h
+2
-0
outputgen.h
src/outputgen.h
+3
-0
outputlist.cpp
src/outputlist.cpp
+1
-0
outputlist.h
src/outputlist.h
+6
-0
pre.l
src/pre.l
+2
-2
rtfgen.cpp
src/rtfgen.cpp
+22
-0
rtfgen.h
src/rtfgen.h
+2
-0
scanner.l
src/scanner.l
+9
-5
sortdict.h
src/sortdict.h
+1
-1
util.cpp
src/util.cpp
+171
-4
No files found.
INSTALL
View file @
05930245
DOXYGEN Version 1.3.9.1
DOXYGEN Version 1.3.9.1
-20041114
Please read the installation section of the manual
(http://www.doxygen.org/install.html) for instructions.
--------
Dimitri van Heesch (
28 Octo
ber 2004)
Dimitri van Heesch (
14 Novem
ber 2004)
README
View file @
05930245
DOXYGEN Version 1.3.9.1
DOXYGEN Version 1.3.9.1
_20041114
Please read INSTALL for compilation instructions.
...
...
@@ -17,4 +17,4 @@ to subscribe to the lists or to visit the archives.
Enjoy,
Dimitri van Heesch (dimitri@stack.nl) (
28 Octo
ber 2004)
Dimitri van Heesch (dimitri@stack.nl) (
14 Novem
ber 2004)
VERSION
View file @
05930245
1.3.9.1
1.3.9.1
-20041114
doc/commands.doc
View file @
05930245
...
...
@@ -51,6 +51,7 @@ documentation:
\refitem cmdcategory \\category
\refitem cmdclass \\class
\refitem cmdcode \\code
\refitem cmdcond \\cond
\refitem cmdcopydoc \\copydoc
\refitem cmddate \\date
\refitem cmddef \\def
...
...
@@ -65,6 +66,7 @@ documentation:
\refitem cmdelseif \\elseif
\refitem cmdem \\em
\refitem cmdendcode \\endcode
\refitem cmdendcond \\endcond
\refitem cmdenddot \\enddot
\refitem cmdendhtmlonly \\endhtmlonly
\refitem cmdendif \\endif
...
...
@@ -223,6 +225,7 @@ doxygen. Unrecognized commands are treated as normal text.
\sa section \ref cmdclass "\\class".
<hr>
\section cmdclass \class <name> [<header-file>] [<header-name>]
\addindex \\class
...
...
@@ -754,6 +757,72 @@ See section \ref memgroup for an example.
sectioning command is encountered. See section \ref cmdauthor "\\author"
for an example.
<hr>
\section cmdcond \cond [<section-label>]
\addindex \\cond
Starts a conditional section that ends with a corresponding
\ref cmdendcond "\\endcond" command, which is typically found in
another comment block. The main purpose of this pair of
commands is to (conditionally) exclude part of a file from processing
(traditionally this could only be achieved using C processor commands).
The section between \\cond and \\endcond commands can be included by
adding its section label to the \ref cfg_enabled_sections "ENABLED_SECTIONS"
configuration option. If the section label is omitted, the section will
be excluded from processing unconditionally.
For conditional sections within a comment block one should
use a \ref cmdif "\\if" ... \ref cmdendif "\\endif" block.
Conditional sections can be nested. In this case a nested section will only
be shown if it and its containing section are included.
Here is an example showing the commands in action:
\verbatim
/** An interface */
class Intf
{
public:
/** A method */
virtual void func() = 0;
/// @cond TEST
/** A method used for testing */
virtual void test() = 0;
/// @endcond
};
/// @cond DEV
/*
* The implementation of the interface
*/
class Implementation : public Intf
{
public:
void func();
/// @cond TEST
void test();
/// @endcond
/// @cond
/** This method is obsolete and does
* not show up in the documentation.
*/
void obsolete();
/// @endcond
};
/// @endcond
\endverbatim
The output will be different depending on whether \c ENABLED_SECTIONS
is empty, \c TEST, \c DEV, or \c DEV \c TEST.
<hr>
\section cmddate \date { date description }
...
...
@@ -803,11 +872,19 @@ See section \ref memgroup for an example.
\sa sections \ref cmdendif "\\endif", \ref cmdifnot "\\ifnot",
\ref cmdelse "\\else", and \ref cmdelseif "\\elseif".
<hr>
\section cmdendcond \endcond
\addindex \\endcond
Ends a conditional section that was started by \ref cmdcond "\\cond".
\sa \ref cmdcond "\\cond".
<hr>
\section cmdendif \endif
\addindex \\endif
Ends a conditional section that was started
with
\c \\if or \c \\ifnot
Ends a conditional section that was started
by
\c \\if or \c \\ifnot
For each \c \\if or \c \\ifnot one and only one matching \c \\endif must follow.
\sa \ref cmdif "\\if", and \ref cmdifnot "\\ifnot".
...
...
doc/config.doc
View file @
05930245
...
...
@@ -73,6 +73,7 @@ followed by the descriptions of the tags grouped by category.
\
refitem
cfg_compact_rtf
COMPACT_RTF
\
refitem
cfg_create_subdirs
CREATE_SUBDIRS
\
refitem
cfg_details_at_top
DETAILS_AT_TOP
\
refitem
cfg_directory_graph
DIRECTORY_GRAPH
\
refitem
cfg_disable_index
DISABLE_INDEX
\
refitem
cfg_distribute_group_doc
DISTRIBUTE_GROUP_DOC
\
refitem
cfg_dot_image_format
DOT_IMAGE_FORMAT
...
...
@@ -609,7 +610,8 @@ function's detailed documentation block.
\addindex ENABLED_SECTIONS
The \c ENABLED_SECTIONS tag can be used to enable conditional
documentation sections, marked by \ref cmdif "\\if" \<section-label\> ...
\ref cmdendif "\\endif" blocks.
\ref cmdendif "\\endif" and \ref cmdcond "\\cond" \<section-label\> ...
\ref cmdendcond "\\endcond" blocks.
\anchor cfg_max_initializer_lines
<dt>\c MAX_INITIALIZER_LINES <dd>
...
...
@@ -1583,10 +1585,18 @@ TAGFILES = file1=loc1 "file2 = loc2" ... </pre>
If
the
\
c
GRAPHICAL_HIERARCHY
and
\
c
HAVE_DOT
tags
are
set
to
\
c
YES
then
doxygen
will
graphical
hierarchy
of
all
classes
instead
of
a
textual
one
.
\
anchor
cfg_directory_graph
<
dt
>\
c
DIRECTORY_GRAPH
<
dd
>
\
addindex
DIRECTORY_GRAPH
If
the
\
c
DIRECTORY_GRAPH
,
\
c
SHOW_DIRECTORIES
and
\
c
HAVE_DOT
options
are
set
to
\
c
YES
then
doxygen
will
show
the
dependencies
a
directory
has
on
other
directories
in
a
graphical
way
.
The
dependency
relations
are
determined
by
the
#
include
relations
between
the
files
in
the
directories
.
\
anchor
cfg_dot_image_format
<
dt
>\
c
DOT_IMAGE_FORMAT
<
dd
>
\
addindex
DOT_IMAGE_FORMAT
The
DOT_IMAGE_FORMAT
tag
can
be
used
to
set
the
image
format
of
the
images
The
\
c
DOT_IMAGE_FORMAT
tag
can
be
used
to
set
the
image
format
of
the
images
generated
by
dot
.
Possible
values
are
gif
,
jpg
,
and
png
.
If
left
blank
png
will
be
used
.
...
...
doc/faq.doc
View file @
05930245
...
...
@@ -79,7 +79,13 @@ document either the class or namespace.
<li><b>How can I make doxygen ignore some code fragment?</b>
<p>
You can use Doxygen's preprocessor for this:
The new and easiest way is to add one comment block
with a \ref cmdcond "\\cond" command at the start and one comment block
with a \ref cmdendcond "\\endcond" command at the end of the piece of
code that should be ignored. This should be within the same file of course.
But you can also use Doxygen's preprocessor for this:
If you put
\verbatim
#ifndef DOXYGEN_SHOULD_SKIP_THIS
...
...
@@ -97,7 +103,10 @@ as <code>PREPROCESSING = YES</code>.
<li><b>How can I change what is after the <code>\#include</code> in the class documentation?</b>
You can document your class like
In most cases you can use STRIP_FROM_INC_PATH to strip a user defined
part of a path.
You can also document your class as follows
\verbatim
/*! \class MyClassName include.h path/include.h
...
...
doc/infoflow.gif
View replaced file @
62d6edc6
View file @
05930245
12.2 KB
|
W:
|
H:
23.9 KB
|
W:
|
H:
2-up
Swipe
Onion skin
doc/install.doc
View file @
05930245
...
...
@@ -385,7 +385,9 @@ Currently, I have only compiled doxygen for Windows using Microsoft's
Visual C++ (version 6.0). For other compilers you may need to edit the
perl script in <code>wintools/make.pl</code> a bit.
Let me know what you had to change if you got Doxygen working with another
compiler.
compiler. If you have Visual Studio you can also use the .dsw file found in
the <code>wintools</code> directory. Note that this file is not maintained
by me, so it might be outdated a little.
If you have Visual C++ 6.0, and the source distribution, you can easily
build doxygen using the project files in the \c wintools directory. If
...
...
@@ -462,57 +464,16 @@ Here is what is required:
commerical version of Qt.
For doxywizard, a complete Qt library is
still a requirement however. You can download the non-commercial version
from Troll-Tech web-site. See doxygen download page for a link.
<li>To generate LaTeX documentation or formulas in HTML you need the tools:
<code>latex</code>, <code>dvips</code> and <code>gswin32</code>.
To get these working under Windows
install the fpTeX distribution. You can find more info at:
http://www.fptex.org/ and download it from CTAN or one of its mirrors.
In the Netherlands for example this would be:
ftp://ftp.easynet.nl/mirror/CTAN/systems/win32/fptex/
Make sure the tools are available from a dos box, by adding the
directory they are in to the search path.
For your information, the LaTeX is freely available set of so
called macros and styles on the top of the famous TeX program
(by famous Donald Knuth) and the accompanied utilities (all
available for free). It is used for high quality
typesetting. The result -- in the form of so called
<code>DVI</code> (DeVice Independent) file -- can be printed or
displayed on various devices preserving exactly the same look up
to the capability of the device. The <code>dvips</code> allows you
to convert the <code>dvi</code> to the high quality PostScript
(i.e. PostScript that can be processed by utilities like
<code>psnup</code>, <code>psbook</code>, <code>psselect</code>,
and others). The derived version of TeX (the pdfTeX) can be used
to produce PDF output instead of DVI, or the PDF can be produced
from PostScript using the utility <code>ps2pdf</code>.
If you want to use MikTeX then you need to select at least the
medium size installation. For really old versions of MikTex or minimal
installations, you may need to download the fancyhdr package separately.
You can find it at:
ftp://ftp.tex.ac.uk/tex-archive/macros/latex/contrib/supported/fancyhdr/
<li>If you want to generate compressed HTML help
(see \ref cfg_generate_htmlhelp "GENERATE_HTMLHELP") in the
config file, then you need the Microsoft HTML help workshop.
You can download it at:
http://msdn.microsoft.com/library/default.asp?url=/library/en-us/htmlhelp/html/vsconHH1Start.asp
still a requirement however. A commercial license to build
doxywizard with the latest Qt library was kindly donated to me
by the nice people at <a href="http://www.trolltech.com">TrollTech</a>.
See doxygen download page for a link.
<li>If you used WinZip to extract the tar archive it will (apparently) not
create empty folders, so you have to add the folders
<code>objects</code> and <code>bin</code> manually in the root of the
distribution before compiling.
<li><a href="http://www.research.att.com/sw/tools/graphviz/">
the Graph visualization toolkit version 1.8.10</a><br>
\latexonly(see {\tt http://www.research.att.com/sw/tools/graphviz/})\endlatexonly.
Needed for the include dependency graphs, the graphical inheritance graphs,
and the collaboration graphs.
</ul>
...
...
@@ -577,23 +538,66 @@ To install doxygen, just copy the binaries from the <code>bin</code> directory
to a location somewhere in the path. Alternatively, you can include
the <code>bin</code> directory of the distribution to the path.
<!--
For running doxywizard you need to install the non-commercial version of
the Qt library first. This library can be downloaded from
http://www.trolltech.com/products/download/qt-win-noncomm.html
-->
There are a couple of tools you may want to install to use all of doxygen's
features:
<ul>
<li>To generate LaTeX documentation or formulas in HTML you need the tools:
<code>latex</code>, <code>dvips</code> and <code>gswin32</code>.
To get these working under Windows
install the fpTeX distribution. You can find more info at:
http://www.fptex.org/ and download it from CTAN or one of its mirrors.
In the Netherlands for example this would be:
ftp://ftp.easynet.nl/mirror/CTAN/systems/win32/fptex/
Make sure the tools are available from a dos box, by adding the
directory they are in to the search path.
For your information, the LaTeX is freely available set of so
called macros and styles on the top of the famous TeX program
(by famous Donald Knuth) and the accompanied utilities (all
available for free). It is used for high quality
typesetting. The result -- in the form of so called
<code>DVI</code> (DeVice Independent) file -- can be printed or
displayed on various devices preserving exactly the same look up
to the capability of the device. The <code>dvips</code> allows you
to convert the <code>dvi</code> to the high quality PostScript
(i.e. PostScript that can be processed by utilities like
<code>psnup</code>, <code>psbook</code>, <code>psselect</code>,
and others). The derived version of TeX (the pdfTeX) can be used
to produce PDF output instead of DVI, or the PDF can be produced
from PostScript using the utility <code>ps2pdf</code>.
If you want to use MikTeX then you need to select at least the
medium size installation. For really old versions of MikTex or minimal
installations, you may need to download the fancyhdr package separately.
You can find it at:
ftp://ftp.tex.ac.uk/tex-archive/macros/latex/contrib/supported/fancyhdr/
<li>If you want to generate compressed HTML help
(see \ref cfg_generate_htmlhelp "GENERATE_HTMLHELP") in the
config file, then you need the Microsoft HTML help workshop.
You can download it at:
http://msdn.microsoft.com/library/default.asp?url=/library/en-us/htmlhelp/html/vsconHH1Start.asp
<li><a href="http://www.research.att.com/sw/tools/graphviz/">
the Graph visualization toolkit version 1.8.10</a><br>
\latexonly(see {\tt http://www.research.att.com/sw/tools/graphviz/})\endlatexonly.
Needed for the include dependency graphs, the graphical inheritance graphs,
and the collaboration graphs.
</ul>
\section build_tools Tools used to develop doxygen
Doxygen was developed and tested under Linux using the following
open-source tools:
<ul>
<li>GCC version
2.95.3
<li>GCC version
3.3.1
<li>GNU flex version 2.5.4
<li>GNU bison version 1.
3
5
<li>GNU make version 3.
79.1
<li>Perl version 5.
005_03
<li>VIM version
5.8
<li>GNU bison version 1.
7
5
<li>GNU make version 3.
80
<li>Perl version 5.
8.1
<li>VIM version
6.2
<li>Mozilla 1.0
<li>Troll Tech's tmake version 1.3 (included in the distribution)
<li>teTeX version 1.0
...
...
doc/language.doc
View file @
05930245
...
...
@@ -23,7 +23,7 @@ text fragments, generated by doxygen, can be produced in languages other
than English (the default). The output language is chosen through the
configuration file (with default name and known as Doxyfile).
Currently (version 1.3.9), 30 languages
Currently (version 1.3.9
.1
), 30 languages
are supported (sorted alphabetically):
Afrikaans, Brazilian Portuguese, Catalan, Chinese, Chinese
Traditional, Croatian, Czech, Danish, Dutch, English, Finnish, French,
...
...
@@ -210,7 +210,7 @@ when the translator was updated.
<td>Serbian</td>
<td>Dejan Milosavljevic</td>
<td>dmilos at email dot com</td>
<td>
1.3.8
</td>
<td>
up-to-date
</td>
</tr>
<tr bgcolor="#ffffff">
<td>Slovak</td>
...
...
@@ -318,7 +318,7 @@ when the translator was updated.
\hline
Russian & Alexandr Chelpanov & {\tt\tiny cav@cryptopro.ru} & up-to-date \\
\hline
Serbian & Dejan Milosavljevic & {\tt\tiny dmilos@email.com} &
1.3.8
\\
Serbian & Dejan Milosavljevic & {\tt\tiny dmilos@email.com} &
up-to-date
\\
\hline
Slovak & Stanislav Kudl\'{a}\v{c} & {\tt\tiny skudlac@pobox.sk} & 1.2.18 \\
\hline
...
...
doc/preprocessing.doc
View file @
05930245
...
...
@@ -74,8 +74,30 @@ and specify the macro definitions after
the \ref cfg_predefined "PREDEFINED" or
\ref cfg_expand_as_defined "EXPAND_AS_DEFINED" tag.
As an example, suppose you have the following obfuscated code fragment
of an abstract base class called \c IUnknown:
A typically example where some help from the preprocessor is needed is
when dealing with Microsoft's __declspec language extension. Here is an
example function.
\verbatim
extern "C" void __declspec(dllexport) ErrorMsg( String aMessage,...);
\endverbatim
When nothing is done, doxygen will be confused and see __declspec as
some sort of function. To help doxygen one typically uses the following
preprocessor settings:
\verbatim
ENABLE_PREPROCESSING = YES
MACRO_EXPANSION = YES
EXPAND_ONLY_PREDEF = YES
PREDEFINED = __declspec(x)=
\endverbatim
This will make sure the __declspec(dllexport) is removed before doxygen
parses the source code.
For a more complex example, suppose you have the following obfuscated
code fragment of an abstract base class called \c IUnknown:
\verbatim
/*! A reference to an IID */
...
...
doc/translator_report.txt
View file @
05930245
(1.3.9)
(1.3.9
.1
)
Doxygen supports the following 30 languages (sorted alphabetically):
...
...
@@ -8,7 +8,7 @@ German, Greek, Hungarian, Italian, Japanese (+En), Korean (+En),
Lithuanian, Norwegian, Polish, Portuguese, Romanian, Russian, Serbian,
Slovak, Slovene, Spanish, Swedish, and Ukrainian.
Of them, 1
3 translators are up-to-date, 17
translators are based on
Of them, 1
4 translators are up-to-date, 16
translators are based on
some adapter class, and 2 are English based.
----------------------------------------------------------------------
...
...
@@ -29,6 +29,7 @@ still may be some details listed even for them:
TranslatorItalian
TranslatorPolish
TranslatorRussian
TranslatorSerbian
TranslatorSwedish
----------------------------------------------------------------------
...
...
@@ -42,7 +43,6 @@ must be implemented to become up-to-date:
TranslatorDanish 1.3.9 6 methods to implement
TranslatorAfrikaans 1.3.9 6 methods to implement
TranslatorSpanish 1.3.8 7 methods to implement
TranslatorSerbian 1.3.8 7 methods to implement
TranslatorLithuanian 1.3.8 7 methods to implement
TranslatorKorean 1.3.8 7 methods to implement
TranslatorChinesetraditional 1.3.8 7 methods to implement
...
...
@@ -452,22 +452,6 @@ TranslatorRomanian (TranslatorAdapter_1_2_16) 22 methods to implement
virtual QCString trRTFTableOfContents()
TranslatorSerbian (TranslatorAdapter_1_3_8) 7 methods to implement
-----------------
Implements 194 of the required methods.
Missing methods (should be implemented):
virtual QCString trDirIndex()
virtual QCString trDirDocumentation()
virtual QCString trDirectories()
virtual QCString trDirDescription()
virtual QCString trSourceFile(QCString & filename)
virtual QCString trDirReference(const char * dirName)
virtual QCString trDir(bool first_capital, bool singular)
TranslatorSlovak (TranslatorAdapter_1_2_18) 20 methods to implement
----------------
...
...
packages/rpm/doxygen.spec
View file @
05930245
Summary: A documentation system for C/C++.
Name: doxygen
Version: 1.3.9.1
Version: 1.3.9.1
_20041114
Release: 1
Epoch: 1
Source0: ftp://ftp.stack.nl/pub/users/dimitri/%{name}-%{version}.src.tar.gz
...
...
src/commentcnv.h
View file @
05930245
...
...
@@ -20,7 +20,8 @@
class
BufStr
;
extern
void
convertCppComments
(
BufStr
*
inBuf
,
BufStr
*
outBuf
);
extern
void
convertCppComments
(
BufStr
*
inBuf
,
BufStr
*
outBuf
,
const
char
*
fileName
);
#endif
src/commentcnv.l
View file @
05930245
...
...
@@ -22,19 +22,36 @@
#include <stdio.h>
#include <stdlib.h>
#include <qstack.h>
#include <qregexp.h>
#include "bufstr.h"
#include "debug.h"
#include "message.h"
#include "config.h"
#include "doxygen.h"
static BufStr *g_inBuf;
static BufStr *g_outBuf;
struct CondCtx
{
CondCtx(int line,QCString id,bool b)
: lineNr(line),sectionId(id), skip(b) {}
int lineNr;
QCString sectionId;
bool skip;
};
static BufStr * g_inBuf;
static BufStr * g_outBuf;
static int g_inBufPos;
static int g_col;
static int g_blockHeadCol;
static bool g_mlBrief;
static int g_readLineCtx;
static bool g_skip;
static QCString g_fileName;
static int g_lineNr;
static int g_condCtx;
static QStack<CondCtx> g_condStack;
static void replaceCommentMarker(const char *s,int len)
{
...
...
@@ -44,6 +61,7 @@ static void replaceCommentMarker(const char *s,int len)
while ((c=*p) && (c==' ' || c=='\t' || c=='\n'))
{
g_outBuf->addChar(c);
g_lineNr += c=='\n';
p++;
}
// replace start of comment marker by spaces
...
...
@@ -82,20 +100,115 @@ static inline int computeIndent(const char *s)
static inline void copyToOutput(const char *s,int len)
{
g_outBuf->addArray(s,len);
int i;
if (g_skip) // only add newlines.
{
for (i=0;i<len;i++)
{
if (s[i]=='\n')
{
g_outBuf->addChar('\n');
g_lineNr++;
}
}
}
else
{
g_outBuf->addArray(s,len);
static int tabSize=Config_getInt("TAB_SIZE");
for (i=0;i<len;i++)
{
switch (s[i])
{
case '\n': g_col=0
; break;
case '\n': g_col=0; g_lineNr++
; break;
case '\t': g_col+=tabSize-(g_col%tabSize); break;
default: g_col++; break;
}
}
}
}
static void startCondSection(const char *sectId)
{
g_condStack.push(new CondCtx(g_lineNr,sectId,g_skip));
if (Config_getList("ENABLED_SECTIONS").find(sectId)!=-1)
{
//printf("*** Section is enabled!\n");
}
else
{
//printf("*** Section is disabled!\n");
g_skip=TRUE;
}
}
static void endCondSection()
{
if (g_condStack.isEmpty())
{
warn(g_fileName,g_lineNr,"Found \\endcond command without matching \\cond");
g_skip=FALSE;
}
else
{
CondCtx *ctx = g_condStack.pop();
g_skip=ctx->skip;
}
}
/** remove and executes \\cond and \\endcond commands in \a s */
static QCString handleCondCmdInAliases(const QCString &s)
{
QCString result;
//printf("handleCondCmdInAliases(%s)\n",s.data());
static QRegExp cmdPat("[\\\\@][a-z_A-Z][a-z_A-Z0-9]*");
int p=0,i,l;
while ((i=cmdPat.match(s,p,&l))!=-1)
{
result+=s.mid(p,i-p);
QCString cmd = s.mid(i+1,l-1);
//printf("Found command %s\n",cmd.data());
if (cmd=="cond")
{
int sp=i+l,ep;
const char *arg=s.data()+sp;
char c;
// skip spaces
while ((c=*arg) && (c==' ' || c=='\t')) arg++,sp++;
// read argument
if (*arg=='\n') // no arg
{
startCondSection(" ");
ep=sp;
}
else // get argument
{
while ((c=*arg) && isId(c)) arg++,ep++;
if (ep>sp)
{
QCString id = s.mid(sp,ep-sp);
//printf("Found conditional section id %s\n",id.data());
startCondSection(id);
}
}
p=ep;
}
else if (cmd=="endcond")
{
endCondSection();
p=i+l;
}
else
{
result+=s.mid(i,l);
p=i+l;
}
}
result+=s.right(s.length()-p);
return result;
}
#undef YY_INPUT
#define YY_INPUT(buf,result,max_size) result=yyread(buf,max_size);
...
...
@@ -122,6 +235,7 @@ CHARLIT (("'"\\[0-7]{1,3}"'")|("'"\\."'")|("'"[^' \\\n]{1,4}"'"))
%x CComment
%x Verbatim
%x ReadLine
%x CondLine
%%
...
...
@@ -213,17 +327,6 @@ CHARLIT (("'"\\[0-7]{1,3}"'")|("'"\\."'")|("'"[^' \\\n]{1,4}"'"))
copyToOutput(yytext,yyleng);
BEGIN(Scan);
}
<CComment>[\\@][a-z_A-Z][a-z_A-Z0-9]* { // expand alias
QCString *pValue=Doxygen::aliasDict[yytext+1];
if (pValue)
{
copyToOutput(pValue->data(),pValue->length());
}
else
{
copyToOutput(yytext,yyleng);
}
}
<CComment>. {
copyToOutput(yytext,yyleng);
}
...
...
@@ -276,11 +379,47 @@ CHARLIT (("'"\\[0-7]{1,3}"'")|("'"\\."'")|("'"[^' \\\n]{1,4}"'"))
copyToOutput(yytext,yyleng);
BEGIN(g_readLineCtx);
}
<ReadLine>[\\@][a-z_A-Z][a-z_A-Z0-9]* { // expand alias
<CComment,ReadLine>("\\\\"|"@@")[a-z_A-Z][a-z_A-Z0-9]*[ \t]* { // escaped command
copyToOutput(yytext,yyleng);
}
<CComment,ReadLine>[\\@]"cond"[ \t]+ { // conditional section
g_condCtx = YY_START;
BEGIN(CondLine);
}
<CComment,ReadLine>[\\@]"endcond"/[^a-z_A-Z0-9] { // end of conditional section
bool oldSkip=g_skip;
endCondSection();
if (YY_START==CComment && oldSkip && !g_skip)
{
//printf("** Adding start of comment!\n");
g_outBuf->addChar('/');
g_outBuf->addChar('*');
}
}
<CondLine>[a-z_A-Z][a-z_A-Z0-9.\-]* {
bool oldSkip=g_skip;
startCondSection(yytext);
if (g_condCtx==CComment && !oldSkip && g_skip)
{
//printf("** Adding terminator for comment!\n");
g_outBuf->addChar('*');
g_outBuf->addChar('/');
}
BEGIN(g_condCtx);
}
<CondLine>[ \t]*
<CComment,ReadLine>[\\@]"cond"[ \t]*\n |
<CondLine>. { // forgot section id?
startCondSection(" "); // fake section id causing the section to be hidden unconditionally
if (*yytext=='\n') g_lineNr++;
if (YY_START==CondLine) BEGIN(g_condCtx);
}
<CComment,ReadLine>[\\@][a-z_A-Z][a-z_A-Z0-9]* { // expand alias
QCString *pValue=Doxygen::aliasDict[yytext+1];
if (pValue)
{
copyToOutput(pValue->data(),pValue->length());
QCString val = handleCondCmdInAliases(*pValue);
copyToOutput(val.data(),val.length());
}
else
{
...
...
@@ -320,16 +459,28 @@ void replaceComment(int offset)
* -# It converts multi-line C++ style comment blocks (that are aligned)
* to C style comment blocks (if MULTILINE_CPP_IS_BRIEF is set to NO).
* -# It replaces aliases with their definition (see ALIASES)
* -# It handles conditional sections (\cond...\endcond blocks)
*/
void convertCppComments(BufStr *inBuf,BufStr *outBuf)
void convertCppComments(BufStr *inBuf,BufStr *outBuf
,const char *fileName
)
{
g_inBuf = inBuf;
g_outBuf = outBuf;
g_inBufPos = 0;
g_col = 0;
g_mlBrief = Config_getBool("MULTILINE_CPP_IS_BRIEF");
g_skip = FALSE;
g_fileName = fileName;
g_lineNr = 0;
g_condStack.clear();
g_condStack.setAutoDelete(TRUE);
BEGIN(Scan);
yylex();
while (!g_condStack.isEmpty())
{
CondCtx *ctx = g_condStack.pop();
warn(g_fileName,ctx->lineNr,"Conditional section with %s does not have "
"a corresponding \\endcond command within this file.",ctx->sectionId.data());
}
if (Debug::isFlagSet(Debug::CommentCnv))
{
msg("-------------\n%s\n-------------\n",g_outBuf->data());
...
...
src/config.l
View file @
05930245
...
...
@@ -2697,6 +2697,15 @@ void Config::create()
TRUE
);
cb->addDependency("HAVE_DOT");
cb = addBool(
"DIRECTORY_GRAPH",
"If the DIRECTORY_GRAPH, SHOW_DIRECTORIES and HAVE_DOT tags are set to YES \n"
"then doxygen will show the dependencies a directory has on other directories \n"
"in a graphical way. The dependency relations are determined by the #include\n"
"relations between the files in the directories.\n",
TRUE
);
cb->addDependency("HAVE_DOT");
ce = addEnum(
"DOT_IMAGE_FORMAT",
"The DOT_IMAGE_FORMAT tag can be used to set the image format of the images \n"
...
...
src/debug.cpp
View file @
05930245
...
...
@@ -57,6 +57,8 @@ static int labelToEnumValue(const char *l)
return
Debug
::
PrintTree
;
else
if
(
label
==
"time"
)
return
Debug
::
Time
;
else
if
(
label
==
"extcmd"
)
return
Debug
::
ExtCmd
;
else
return
0
;
}
...
...
src/debug.h
View file @
05930245
...
...
@@ -31,7 +31,8 @@ class Debug
CommentCnv
=
0x00000020
,
Validate
=
0x00000040
,
PrintTree
=
0x00000080
,
Time
=
0x00000100
Time
=
0x00000100
,
ExtCmd
=
0x00000200
};
static
void
print
(
DebugMask
mask
,
int
prio
,
const
char
*
fmt
,...);
static
void
setFlag
(
const
char
*
label
);
...
...
src/dirdef.cpp
View file @
05930245
...
...
@@ -5,6 +5,7 @@
#include "outputlist.h"
#include "language.h"
#include "message.h"
#include "dot.h"
//----------------------------------------------------------------------
// method implementation
...
...
@@ -27,7 +28,6 @@ DirDef::DirDef(const char *path) : Definition(path,1,path)
m_shortName
=
m_shortName
.
mid
(
pi
+
1
);
}
m_subdirs
.
setAutoDelete
(
TRUE
);
m_fileList
=
new
FileList
;
m_classSDict
=
new
ClassSDict
(
17
);
m_usedDirs
=
new
QDict
<
UsedDir
>
(
257
);
...
...
@@ -141,6 +141,21 @@ void DirDef::writeDocumentation(OutputList &ol)
Doxygen
::
tagFile
<<
" <filename>"
<<
convertToXML
(
getOutputFileBase
())
<<
Doxygen
::
htmlFileExtension
<<
"</filename>"
<<
endl
;
}
// write graph dependency graph
if
(
Config_getBool
(
"DIRECTORY_GRAPH"
)
&&
Config_getBool
(
"HAVE_DOT"
))
{
DotDirDeps
dirDep
(
this
);
if
(
!
dirDep
.
isTrivial
())
{
msg
(
"Generating dependency graph for directory %s
\n
"
,
displayName
().
data
());
ol
.
disable
(
OutputGenerator
::
Man
);
ol
.
newParagraph
();
ol
.
startDirDepGraph
();
//TODO: ol.parseText(theTranslator->trDirDepGraph());
ol
.
endDirDepGraph
(
dirDep
);
ol
.
enableAll
();
}
}
ol
.
startMemberSections
();
// write subdir list
...
...
@@ -154,7 +169,7 @@ void DirDef::writeDocumentation(OutputList &ol)
while
(
dd
)
{
ol
.
startMemberItem
(
0
);
ol
.
parseText
(
theTranslator
->
trDir
(
FALSE
,
TRUE
));
ol
.
parseText
(
theTranslator
->
trDir
(
FALSE
,
TRUE
)
+
" "
);
ol
.
insertMemberAlign
();
ol
.
writeObjectLink
(
dd
->
getReference
(),
dd
->
getOutputFileBase
(),
0
,
dd
->
shortName
());
ol
.
endMemberItem
();
...
...
@@ -232,13 +247,11 @@ void DirDef::writeDocumentation(OutputList &ol)
ol
.
popGeneratorState
();
}
void
DirDef
::
writePathFragment
(
OutputList
&
ol
)
void
DirDef
::
writePathFragment
(
OutputList
&
ol
)
const
{
if
(
getOuterScope
()
!=
Doxygen
::
globalScope
&&
getOuterScope
()
->
definitionType
()
==
Definition
::
TypeDir
)
if
(
m_parent
)
{
//printf("getOuterScope %s\n",getOuterScope()->name().data());
((
DirDef
*
)
getOuterScope
())
->
writePathFragment
(
ol
);
m_parent
->
writePathFragment
(
ol
);
ol
.
writeString
(
" / "
);
}
ol
.
writeObjectLink
(
getReference
(),
getOutputFileBase
(),
0
,
shortName
());
...
...
@@ -276,7 +289,8 @@ void DirDef::setLevel()
/** Add as "uses" dependency between \a this dir and \a dir,
* that was caused by a dependency on file \a fd.
*/
void
DirDef
::
addUsesDependency
(
DirDef
*
dir
,
FileDef
*
fd
,
bool
inherited
)
void
DirDef
::
addUsesDependency
(
DirDef
*
dir
,
FileDef
*
srcFd
,
FileDef
*
dstFd
,
bool
inherited
)
{
if
(
this
==
dir
)
return
;
// do not add self-dependencies
//printf(" > add dependency %s->%s due to %s\n",shortName().data(),
...
...
@@ -287,11 +301,12 @@ void DirDef::addUsesDependency(DirDef *dir,FileDef *fd,bool inherited)
UsedDir
*
usedDir
=
m_usedDirs
->
find
(
dir
->
getOutputFileBase
());
if
(
usedDir
)
// dir dependency already present
{
FileDef
*
usedFd
=
usedDir
->
findFile
(
fd
->
getOutputFileBase
());
if
(
usedFd
==
0
)
// new file dependency
FilePair
*
usedPair
=
usedDir
->
findFilePair
(
srcFd
->
getOutputFileBase
()
+
dstFd
->
getOutputFileBase
());
if
(
usedPair
==
0
)
// new file dependency
{
//printf(" => new file\n");
usedDir
->
addFile
(
f
d
);
usedDir
->
addFile
Dep
(
srcFd
,
dstF
d
);
added
=
TRUE
;
}
else
...
...
@@ -303,19 +318,19 @@ void DirDef::addUsesDependency(DirDef *dir,FileDef *fd,bool inherited)
{
//printf(" => new file\n");
usedDir
=
new
UsedDir
(
dir
,
inherited
);
usedDir
->
addFile
(
f
d
);
usedDir
->
addFile
Dep
(
srcFd
,
dstF
d
);
m_usedDirs
->
insert
(
dir
->
getOutputFileBase
(),
usedDir
);
added
=
TRUE
;
}
if
(
added
&&
dir
->
parent
())
{
// add relation to parent of used dir
addUsesDependency
(
dir
->
parent
(),
f
d
,
inherited
);
addUsesDependency
(
dir
->
parent
(),
srcFd
,
dstF
d
,
inherited
);
}
if
(
parent
())
{
// add relation for the parent of this dir as well
parent
()
->
addUsesDependency
(
dir
,
f
d
,
TRUE
);
parent
()
->
addUsesDependency
(
dir
,
srcFd
,
dstF
d
,
TRUE
);
}
}
...
...
@@ -345,7 +360,7 @@ void DirDef::computeDependencies()
if
(
usedDir
)
{
// add dependency: thisDir->usedDir
addUsesDependency
(
usedDir
,
ii
->
fileDef
,
FALSE
);
addUsesDependency
(
usedDir
,
fd
,
ii
->
fileDef
,
FALSE
);
}
}
}
...
...
@@ -364,31 +379,46 @@ bool DirDef::isParentOf(DirDef *dir) const
return
FALSE
;
}
bool
DirDef
::
depGraphIsTrivial
()
const
{
return
FALSE
;
}
//----------------------------------------------------------------------
int
FilePairDict
::
compareItems
(
GCI
item1
,
GCI
item2
)
{
FilePair
*
left
=
(
FilePair
*
)
item1
;
FilePair
*
right
=
(
FilePair
*
)
item2
;
int
orderHi
=
stricmp
(
left
->
source
()
->
name
(),
right
->
source
()
->
name
());
int
orderLo
=
stricmp
(
left
->
destination
()
->
name
(),
right
->
destination
()
->
name
());
return
orderHi
==
0
?
orderLo
:
orderHi
;
}
//----------------------------------------------------------------------
UsedDir
::
UsedDir
(
DirDef
*
dir
,
bool
inherited
)
:
m_dir
(
dir
),
m_inherited
(
inherited
)
m_dir
(
dir
),
m_
filePairs
(
7
),
m_
inherited
(
inherited
)
{
m_filePairs
.
setAutoDelete
(
TRUE
);
}
UsedDir
::~
UsedDir
()
{
}
void
UsedDir
::
addFile
(
FileDef
*
f
d
)
void
UsedDir
::
addFile
Dep
(
FileDef
*
srcFd
,
FileDef
*
dstF
d
)
{
m_files
.
insert
(
fd
->
getOutputFileBase
(),
fd
);
m_filePairs
.
inSort
(
srcFd
->
getOutputFileBase
()
+
dstFd
->
getOutputFileBase
(),
new
FilePair
(
srcFd
,
dstFd
));
}
File
Def
*
UsedDir
::
findFile
(
const
char
*
name
)
File
Pair
*
UsedDir
::
findFilePair
(
const
char
*
name
)
{
QCString
n
=
name
;
return
n
.
isEmpty
()
?
0
:
m_files
.
find
(
n
);
return
n
.
isEmpty
()
?
0
:
m_file
Pair
s
.
find
(
n
);
}
//----------------------------------------------------------------------
// helper functions
DirDef
*
DirDef
::
createNewDir
(
const
char
*
path
)
{
ASSERT
(
path
!=
0
);
...
...
@@ -442,13 +472,27 @@ void DirDef::writeDepGraph(QTextStream &t)
{
t
<<
"digraph G {
\n
"
;
t
<<
" compound=true
\n
"
;
t
<<
" node [ fontsize=10, fontname=
\"
Helvetica
\"
];
\n
"
;
t
<<
" edge [ labelfontsize=9, labelfontname=
\"
Helvetica
\"
];
\n
"
;
QDict
<
DirDef
>
dirsInGraph
(
257
);
dirsInGraph
.
insert
(
getOutputFileBase
(),
this
);
if
(
parent
())
{
t
<<
" subgraph cluster"
<<
parent
()
->
getOutputFileBase
()
<<
" {
\n
"
;
t
<<
" graph [ bgcolor=
\"
#ddddee
\"
, pencolor=
\"
black
\"
, label=
\"
"
<<
parent
()
->
shortName
()
<<
"
\"
fontname=
\"
Helvetica
\"
, fontsize=10, URL=
\"
"
;
t
<<
parent
()
->
getOutputFileBase
()
<<
Doxygen
::
htmlFileExtension
;
t
<<
"
\"
]
\n
"
;
}
if
(
isCluster
())
{
t
<<
" subgraph cluster"
<<
getOutputFileBase
()
<<
" {
\n
"
;
t
<<
" graph [ bgcolor=
\"
#eeeeff
\"
, pencolor=
\"
black
\"
, label=
\"\"
"
<<
" URL=
\"
"
<<
getOutputFileBase
()
<<
Doxygen
::
htmlFileExtension
<<
"
\"
];
\n
"
;
t
<<
" "
<<
getOutputFileBase
()
<<
" [shape=plaintext label=
\"
"
<<
shortName
()
<<
"
\"
];
\n
"
;
...
...
@@ -461,8 +505,15 @@ void DirDef::writeDepGraph(QTextStream &t)
<<
sdir
->
shortName
()
<<
"
\"
"
;
if
(
sdir
->
isCluster
())
{
t
<<
" color=
\"
red
\"
fillcolor=
\"
white
\"
style=
\"
filled
\"
"
;
t
<<
" color=
\"
red
\"
"
;
}
else
{
t
<<
" color=
\"
black
\"
"
;
}
t
<<
" fillcolor=
\"
white
\"
style=
\"
filled
\"
"
;
t
<<
" URL=
\"
"
<<
sdir
->
getOutputFileBase
()
<<
Doxygen
::
htmlFileExtension
<<
"
\"
"
;
t
<<
"];
\n
"
;
dirsInGraph
.
insert
(
sdir
->
getOutputFileBase
(),
sdir
);
}
...
...
@@ -470,7 +521,14 @@ void DirDef::writeDepGraph(QTextStream &t)
}
else
{
t
<<
getOutputFileBase
()
<<
" [shape=box label=
\"
"
<<
shortName
()
<<
"
\"
];
\n
"
;
t
<<
" "
<<
getOutputFileBase
()
<<
" [shape=box, label=
\"
"
<<
shortName
()
<<
"
\"
, style=
\"
filled
\"
, fillcolor=
\"
#eeeeff
\"
,"
<<
" pencolor=
\"
black
\"
, URL=
\"
"
<<
getOutputFileBase
()
<<
Doxygen
::
htmlFileExtension
<<
"
\"
];
\n
"
;
}
if
(
parent
())
{
t
<<
" }
\n
"
;
}
// add nodes for other used directories
...
...
@@ -500,7 +558,8 @@ void DirDef::writeDepGraph(QTextStream &t)
{
t
<<
" color=
\"
red
\"
fillcolor=
\"
white
\"
style=
\"
filled
\"
"
;
}
t
<<
"];
\n
"
;
t
<<
" URL=
\"
"
<<
usedDir
->
getOutputFileBase
()
<<
Doxygen
::
htmlFileExtension
<<
"
\"
];
\n
"
;
dirsInGraph
.
insert
(
usedDir
->
getOutputFileBase
(),
usedDir
);
break
;
}
...
...
@@ -523,11 +582,20 @@ void DirDef::writeDepGraph(QTextStream &t)
!
usedDir
->
isParentOf
(
dir
)
&&
// don't point to own parent
dirsInGraph
.
find
(
usedDir
->
getOutputFileBase
()))
// only point to nodes that are in the graph
{
int
nrefs
=
udir
->
files
().
count
();
QCString
relationName
;
relationName
.
sprintf
(
"dir_%06d_%06d"
,
dir
->
m_dirCount
,
usedDir
->
m_dirCount
);
if
(
Doxygen
::
dirRelations
.
find
(
relationName
)
==
0
)
{
// new relation
Doxygen
::
dirRelations
.
append
(
relationName
,
new
DirRelation
(
relationName
,
dir
,
udir
));
}
int
nrefs
=
udir
->
filePairs
().
count
();
t
<<
" "
<<
dir
->
getOutputFileBase
()
<<
"->"
<<
usedDir
->
getOutputFileBase
();
t
<<
" [headlabel=
\"
"
<<
nrefs
<<
"
\"
headhref=
\"
http://www.doxygen.org
\"
]"
;
t
<<
";
\n
"
;
t
<<
" [headlabel=
\"
"
<<
nrefs
<<
"
\"
, labeldistance=1.5"
;
t
<<
" headhref=
\"
"
<<
relationName
<<
Doxygen
::
htmlFileExtension
<<
"
\"
];
\n
"
;
}
}
}
...
...
@@ -535,6 +603,85 @@ void DirDef::writeDepGraph(QTextStream &t)
t
<<
"}
\n
"
;
}
//----------------------------------------------------------------------
static
void
writePartialDirPath
(
OutputList
&
ol
,
const
DirDef
*
root
,
const
DirDef
*
target
)
{
if
(
target
->
parent
()
!=
root
)
{
writePartialDirPath
(
ol
,
root
,
target
->
parent
());
ol
.
writeString
(
" / "
);
}
ol
.
writeObjectLink
(
target
->
getReference
(),
target
->
getOutputFileBase
(),
0
,
target
->
shortName
());
}
static
void
writePartialFilePath
(
OutputList
&
ol
,
const
DirDef
*
root
,
const
FileDef
*
fd
)
{
if
(
fd
->
getDirDef
()
&&
fd
->
getDirDef
()
!=
root
)
{
writePartialDirPath
(
ol
,
root
,
fd
->
getDirDef
());
ol
.
writeString
(
" / "
);
}
if
(
fd
->
isLinkable
())
{
ol
.
writeObjectLink
(
fd
->
getReference
(),
fd
->
getOutputFileBase
(),
0
,
fd
->
name
());
}
else
{
ol
.
startBold
();
ol
.
docify
(
fd
->
name
());
ol
.
endBold
();
}
}
void
DirRelation
::
writeDocumentation
(
OutputList
&
ol
)
{
ol
.
pushGeneratorState
();
ol
.
disableAllBut
(
OutputGenerator
::
Html
);
QCString
shortTitle
=
m_src
->
shortName
()
+
" → "
+
m_dst
->
dir
()
->
shortName
()
+
" Relation"
;
//theTranslator->trDirRelation(m_shortName);
QCString
title
=
m_src
->
displayName
()
+
" -> "
+
m_dst
->
dir
()
->
shortName
()
+
" Relation"
;
//theTranslator->trDirRelation(m_dispName);
startFile
(
ol
,
getOutputFileBase
(),
getOutputFileBase
(),
title
);
// write navigation path
m_src
->
writeNavigationPath
(
ol
);
//startTitle(ol,getOutputFileBase());
// ol.parseText(shortTitle);
//endTitle(ol,getOutputFileBase(),title);
ol
.
writeString
(
"<h3>"
+
shortTitle
+
"</h3>"
);
ol
.
writeString
(
"<table class=
\"
dirtab
\"
>"
);
ol
.
writeString
(
"<tr class=
\"
dirtab
\"
>"
);
ol
.
writeString
(
"<th class=
\"
dirtab
\"
>File in "
);
m_src
->
writePathFragment
(
ol
);
ol
.
writeString
(
"</th>"
);
ol
.
writeString
(
"<th class=
\"
dirtab
\"
>Includes file in "
);
m_dst
->
dir
()
->
writePathFragment
(
ol
);
ol
.
writeString
(
"</th>"
);
ol
.
writeString
(
"</tr>"
);
SDict
<
FilePair
>::
Iterator
fpi
(
m_dst
->
filePairs
());
FilePair
*
fp
;
for
(
fpi
.
toFirst
();(
fp
=
fpi
.
current
());
++
fpi
)
{
ol
.
writeString
(
"<tr class=
\"
dirtab
\"
>"
);
ol
.
writeString
(
"<td class=
\"
dirtab
\"
>"
);
writePartialFilePath
(
ol
,
m_src
,
fp
->
source
());
ol
.
writeString
(
"</td>"
);
ol
.
writeString
(
"<td class=
\"
dirtab
\"
>"
);
writePartialFilePath
(
ol
,
m_dst
->
dir
(),
fp
->
destination
());
ol
.
writeString
(
"</td>"
);
ol
.
writeString
(
"</tr>"
);
}
ol
.
writeString
(
"</table>"
);
endFile
(
ol
);
ol
.
popGeneratorState
();
}
//----------------------------------------------------------------------
// external functions
...
...
@@ -678,5 +825,14 @@ void generateDirDocs(OutputList &ol)
{
dir
->
writeDocumentation
(
ol
);
}
if
(
Config_getBool
(
"DIRECTORY_GRAPH"
))
{
SDict
<
DirRelation
>::
Iterator
rdi
(
Doxygen
::
dirRelations
);
DirRelation
*
dr
;
for
(
rdi
.
toFirst
();(
dr
=
rdi
.
current
());
++
rdi
)
{
dr
->
writeDocumentation
(
ol
);
}
}
}
src/dirdef.h
View file @
05930245
...
...
@@ -34,12 +34,14 @@ class QTextStream;
class
DirDef
;
/** A list of directories */
class
DirList
:
public
QList
<
DirDef
>
{
public
:
int
compareItems
(
GCI
item1
,
GCI
item2
);
};
/** A directory */
class
DirDef
:
public
Definition
{
public
:
...
...
@@ -63,23 +65,25 @@ class DirDef : public Definition
DirDef
*
parent
()
const
{
return
m_parent
;
}
const
QDict
<
UsedDir
>
*
usedDirs
()
const
{
return
m_usedDirs
;
}
bool
isParentOf
(
DirDef
*
dir
)
const
;
bool
depGraphIsTrivial
()
const
;
// generate output
void
writeDetailedDocumentation
(
OutputList
&
ol
);
void
writeDocumentation
(
OutputList
&
ol
);
void
writeNavigationPath
(
OutputList
&
ol
);
void
writeDepGraph
(
QTextStream
&
t
);
void
writePathFragment
(
OutputList
&
ol
)
const
;
static
DirDef
*
mergeDirectoryInTree
(
const
QCString
&
path
);
bool
visited
;
private
:
friend
void
computeDirDependencies
();
void
writePathFragment
(
OutputList
&
ol
);
void
setLevel
();
static
DirDef
*
createNewDir
(
const
char
*
path
);
static
bool
matchPath
(
const
QCString
&
path
,
QStrList
&
l
);
void
addUsesDependency
(
DirDef
*
usedDir
,
FileDef
*
fd
,
bool
inherited
);
void
addUsesDependency
(
DirDef
*
usedDir
,
FileDef
*
srcFd
,
FileDef
*
dstFd
,
bool
inherited
);
void
computeDependencies
();
DirList
m_subdirs
;
...
...
@@ -93,23 +97,59 @@ class DirDef : public Definition
QDict
<
UsedDir
>
*
m_usedDirs
;
};
class
FilePair
{
public
:
FilePair
(
FileDef
*
src
,
FileDef
*
dst
)
:
m_src
(
src
),
m_dst
(
dst
)
{}
const
FileDef
*
source
()
const
{
return
m_src
;
}
const
FileDef
*
destination
()
const
{
return
m_dst
;
}
private
:
FileDef
*
m_src
;
FileDef
*
m_dst
;
};
class
FilePairDict
:
public
SDict
<
FilePair
>
{
public
:
FilePairDict
(
int
size
)
:
SDict
<
FilePair
>
(
size
)
{}
int
compareItems
(
GCI
item1
,
GCI
item2
);
};
/** Usage information of a directory . */
class
UsedDir
{
public
:
UsedDir
(
DirDef
*
dir
,
bool
inherited
);
virtual
~
UsedDir
();
void
addFile
(
FileDef
*
f
d
);
File
Def
*
findFile
(
const
char
*
name
);
const
QDict
<
FileDef
>
&
files
()
const
{
return
m_file
s
;
}
void
addFile
Dep
(
FileDef
*
srcFd
,
FileDef
*
dstF
d
);
File
Pair
*
findFilePair
(
const
char
*
name
);
const
FilePairDict
&
filePairs
()
const
{
return
m_filePair
s
;
}
const
DirDef
*
dir
()
const
{
return
m_dir
;
}
bool
inherited
()
const
{
return
m_inherited
;
}
private
:
DirDef
*
m_dir
;
QDict
<
FileDef
>
m_file
s
;
FilePairDict
m_filePair
s
;
bool
m_inherited
;
};
/** A usage relation between two direction. */
class
DirRelation
{
public
:
DirRelation
(
const
QCString
&
name
,
DirDef
*
src
,
UsedDir
*
dst
)
:
m_name
(
name
),
m_src
(
src
),
m_dst
(
dst
)
{}
DirDef
*
source
()
const
{
return
m_src
;
}
UsedDir
*
destination
()
const
{
return
m_dst
;
}
void
writeDocumentation
(
OutputList
&
ol
);
QCString
getOutputFileBase
()
const
{
return
m_name
;
}
private
:
QCString
m_name
;
DirDef
*
m_src
;
UsedDir
*
m_dst
;
};
inline
int
DirList
::
compareItems
(
GCI
item1
,
GCI
item2
)
{
return
stricmp
(((
DirDef
*
)
item1
)
->
shortName
(),((
DirDef
*
)
item2
)
->
shortName
());
...
...
src/docparser.cpp
View file @
05930245
...
...
@@ -4367,7 +4367,7 @@ reparsetoken:
k
!=
DocNode
::
Kind_SimpleSect
&&
k
!=
DocNode
::
Kind_AutoList
&&
k
!=
DocNode
::
Kind_SimpleList
&&
k
!=
DocNode
::
Kind_Verbatim
&&
/*k!=DocNode::Kind_Verbatim &&*/
k
!=
DocNode
::
Kind_HtmlHeader
&&
k
!=
DocNode
::
Kind_ParamSect
&&
k
!=
DocNode
::
Kind_XRefItem
...
...
@@ -4518,7 +4518,7 @@ reparsetoken:
}
else
if
(
retval
==
RetVal_OK
)
{
// the command ended normally, keep scann
er
for new tokens.
// the command ended normally, keep scann
ing
for new tokens.
retval
=
0
;
}
else
if
(
retval
==
TK_LISTITEM
||
retval
==
TK_ENDLIST
||
retval
==
TK_WORD
)
...
...
src/dot.cpp
View file @
05930245
...
...
@@ -27,6 +27,7 @@
#include "scanner.h"
#include "defargs.h"
#include "docparser.h"
#include "debug.h"
#include <qdir.h>
#include <qfile.h>
...
...
@@ -1927,7 +1928,7 @@ DotInclDepGraph::DotInclDepGraph(FileDef *fd,int maxRecursionDepth,bool inverse)
m_diskName
=
fd
->
getFileBase
().
copy
();
QCString
tmp_url
=
fd
->
getReference
()
+
"$"
+
fd
->
getFileBase
();
m_startNode
=
new
DotNode
(
m_curNodeNumber
++
,
fd
->
n
ame
(),
fd
->
docN
ame
(),
tmp_url
.
data
(),
0
,
// distance
TRUE
// root node
...
...
@@ -1965,7 +1966,7 @@ QCString DotInclDepGraph::writeGraph(QTextStream &out,
err
(
"Error: Output dir %s does not exist!
\n
"
,
path
);
exit
(
1
);
}
QCString
oldDir
=
convertToQCString
(
QDir
::
currentDirPath
());
// go to the output directory (i.e. path)
// go to the
html
output directory (i.e. path)
QDir
::
setCurrent
(
d
.
absPath
());
QDir
thisDir
;
...
...
@@ -1978,12 +1979,12 @@ QCString DotInclDepGraph::writeGraph(QTextStream &out,
QCString
imgExt
=
Config_getEnum
(
"DOT_IMAGE_FORMAT"
);
QCString
md5
=
computeMd5Signature
(
m_startNode
,
// root
DotNode
::
Dependency
,
// gt
DotNode
::
CallGraph
,
// gt
format
,
// format
FALSE
,
// lrRank
TRUE
,
// lrRank
FALSE
,
// renderParents
QMIN
(
m_recDepth
,
m_maxDistance
),
// maxDist
!
m_inverse
// backArrows
FALSE
// backArrows
);
if
(
checkAndUpdateMd5Signature
(
baseName
,
md5
)
||
!
QFileInfo
(
baseName
+
".map"
).
exists
()
...
...
@@ -1993,11 +1994,11 @@ QCString DotInclDepGraph::writeGraph(QTextStream &out,
QMIN
(
m_recDepth
,
m_maxDistance
),
// maxDist
baseName
,
// baseName
thisDir
,
// thisDir
DotNode
::
Dependency
,
// gt
DotNode
::
CallGraph
,
// gt
format
,
// format
FALSE
,
// lrRank
TRUE
,
// lrRank
FALSE
,
// renderParents
!
m_inverse
// backArrows
FALSE
// backArrows
);
if
(
format
==
BITMAP
)
{
...
...
@@ -2045,8 +2046,6 @@ QCString DotInclDepGraph::writeGraph(QTextStream &out,
}
}
}
if
(
Config_getBool
(
"DOT_CLEANUP"
))
thisDir
.
remove
(
baseName
+
".dot"
);
}
if
(
format
==
BITMAP
&&
generateImageMap
)
...
...
@@ -2054,7 +2053,6 @@ QCString DotInclDepGraph::writeGraph(QTextStream &out,
out
<<
"<p><center><img src=
\"
"
<<
relPath
<<
baseName
<<
"."
<<
imgExt
<<
"
\"
border=
\"
0
\"
usemap=
\"
#"
<<
mapName
<<
"_map
\"
alt=
\"
"
;
if
(
m_inverse
)
out
<<
"Included by dependency graph"
;
else
out
<<
"Include dependency graph"
;
out
<<
"
\"
>"
;
out
<<
"</center>"
<<
endl
;
QString
tmpstr
;
...
...
@@ -2066,6 +2064,7 @@ QCString DotInclDepGraph::writeGraph(QTextStream &out,
out
<<
tmpstr
;
out
<<
"</map>"
<<
endl
;
}
//thisDir.remove(baseName+".map");
}
else
if
(
format
==
EPS
)
{
...
...
@@ -2076,7 +2075,6 @@ QCString DotInclDepGraph::writeGraph(QTextStream &out,
QDir
::
setCurrent
(
oldDir
);
return
baseName
;
}
int
maxWidth
=
420
;
/* approx. page width in points */
out
<<
"
\\
begin{figure}[H]
\n
"
...
...
@@ -2088,6 +2086,8 @@ QCString DotInclDepGraph::writeGraph(QTextStream &out,
"
\\
end{figure}
\n
"
;
}
if
(
Config_getBool
(
"DOT_CLEANUP"
))
thisDir
.
remove
(
baseName
+
".dot"
);
QDir
::
setCurrent
(
oldDir
);
return
baseName
;
}
...
...
@@ -2338,7 +2338,7 @@ bool DotCallGraph::isTrivial() const
//-------------------------------------------------------------
DotDirDeps
::
DotDirDeps
(
DirDef
*
)
DotDirDeps
::
DotDirDeps
(
DirDef
*
dir
)
:
m_dir
(
dir
)
{
}
...
...
@@ -2346,6 +2346,142 @@ DotDirDeps::~DotDirDeps()
{
}
QCString
DotDirDeps
::
writeGraph
(
QTextStream
&
out
,
GraphOutputFormat
format
,
const
char
*
path
,
const
char
*
relPath
,
bool
generateImageMap
)
{
QDir
d
(
path
);
// store the original directory
if
(
!
d
.
exists
())
{
err
(
"Error: Output dir %s does not exist!
\n
"
,
path
);
exit
(
1
);
}
QCString
oldDir
=
convertToQCString
(
QDir
::
currentDirPath
());
// go to the html output directory (i.e. path)
QDir
::
setCurrent
(
d
.
absPath
());
QDir
thisDir
;
QCString
baseName
=
m_dir
->
getOutputFileBase
()
+
"_dep"
;
QCString
mapName
=
baseName
;
QCString
imgExt
=
Config_getEnum
(
"DOT_IMAGE_FORMAT"
);
// todo: create check, update md5 checksum
{
QFile
f
(
baseName
+
".dot"
);
if
(
!
f
.
open
(
IO_WriteOnly
))
{
err
(
"Cannot create file %s.dot for writing!
\n
"
,
baseName
.
data
());
}
QTextStream
t
(
&
f
);
m_dir
->
writeDepGraph
(
t
);
f
.
close
();
if
(
format
==
BITMAP
)
{
// run dot to create a bitmap image
QCString
dotArgs
(
maxCmdLine
);
QCString
imgName
=
baseName
+
"."
+
imgExt
;
dotArgs
.
sprintf
(
"
\"
%s.dot
\"
-T%s -o
\"
%s
\"
"
,
baseName
.
data
(),
imgExt
.
data
(),
imgName
.
data
());
if
(
generateImageMap
)
{
// run dot also to create an image map
dotArgs
+=
QCString
(
maxCmdLine
).
sprintf
(
" -Timap -o
\"
%s.map
\"
"
,
baseName
.
data
());
}
if
(
iSystem
(
Config_getString
(
"DOT_PATH"
)
+
"dot"
,
dotArgs
)
!=
0
)
{
err
(
"Problems running dot. Check your installation!
\n
"
);
QDir
::
setCurrent
(
oldDir
);
return
baseName
;
}
checkDotResult
(
imgName
);
}
else
if
(
format
==
EPS
)
{
// run dot to create a .eps image
QCString
dotArgs
(
maxCmdLine
);
dotArgs
.
sprintf
(
"-Tps
\"
%s.dot
\"
-o
\"
%s.eps
\"
"
,
baseName
.
data
(),
baseName
.
data
());
if
(
iSystem
(
Config_getString
(
"DOT_PATH"
)
+
"dot"
,
dotArgs
)
!=
0
)
{
err
(
"Problems running dot. Check your installation!
\n
"
);
QDir
::
setCurrent
(
oldDir
);
return
baseName
;
}
if
(
Config_getBool
(
"USE_PDFLATEX"
))
{
QCString
epstopdfArgs
(
maxCmdLine
);
epstopdfArgs
.
sprintf
(
"
\"
%s.eps
\"
--outfile=
\"
%s.pdf
\"
"
,
baseName
.
data
(),
baseName
.
data
());
if
(
iSystem
(
"epstopdf"
,
epstopdfArgs
,
TRUE
)
!=
0
)
{
err
(
"Error: Problems running epstopdf. Check your TeX installation!
\n
"
);
QDir
::
setCurrent
(
oldDir
);
return
baseName
;
}
}
}
}
if
(
format
==
BITMAP
&&
generateImageMap
)
{
out
<<
"<p><center><img src=
\"
"
<<
relPath
<<
baseName
<<
"."
<<
imgExt
<<
"
\"
border=
\"
0
\"
usemap=
\"
#"
<<
mapName
<<
"_map
\"
alt=
\"
"
;
out
<<
m_dir
->
displayName
();
out
<<
"
\"
>"
;
out
<<
"</center>"
<<
endl
;
QString
tmpstr
;
QTextOStream
tmpout
(
&
tmpstr
);
convertMapFile
(
tmpout
,
baseName
+
".map"
,
relPath
,
TRUE
);
if
(
!
tmpstr
.
isEmpty
())
{
out
<<
"<map name=
\"
"
<<
mapName
<<
"_map
\"
>"
<<
endl
;
out
<<
tmpstr
;
out
<<
"</map>"
<<
endl
;
}
else
{
//printf("Map is empty!\n");
}
//thisDir.remove(baseName+".map");
}
else
if
(
format
==
EPS
)
{
int
width
,
height
;
if
(
!
readBoundingBoxEPS
(
baseName
+
".eps"
,
&
width
,
&
height
))
{
err
(
"Error: Could not extract bounding box from .eps!
\n
"
);
QDir
::
setCurrent
(
oldDir
);
return
baseName
;
}
int
maxWidth
=
420
;
/* approx. page width in points */
out
<<
"
\\
begin{figure}[H]
\n
"
"
\\
begin{center}
\n
"
"
\\
leavevmode
\n
"
"
\\
includegraphics[width="
<<
QMIN
(
width
/
2
,
maxWidth
)
<<
"pt]{"
<<
baseName
<<
"}
\n
"
"
\\
end{center}
\n
"
"
\\
end{figure}
\n
"
;
}
if
(
Config_getBool
(
"DOT_CLEANUP"
))
thisDir
.
remove
(
baseName
+
".dot"
);
QDir
::
setCurrent
(
oldDir
);
return
baseName
;
}
bool
DotDirDeps
::
isTrivial
()
const
{
return
m_dir
->
depGraphIsTrivial
();
}
//-------------------------------------------------------------
void
generateGraphLegend
(
const
char
*
path
)
...
...
src/dot.h
View file @
05930245
...
...
@@ -207,6 +207,14 @@ class DotDirDeps
public
:
DotDirDeps
(
DirDef
*
dir
);
~
DotDirDeps
();
bool
isTrivial
()
const
;
QCString
writeGraph
(
QTextStream
&
out
,
GraphOutputFormat
format
,
const
char
*
path
,
const
char
*
relPath
,
bool
writeImageMap
=
TRUE
);
private
:
DirDef
*
m_dir
;
};
void
generateGraphLegend
(
const
char
*
path
);
...
...
src/doxygen.cpp
View file @
05930245
...
...
@@ -122,6 +122,7 @@ bool Doxygen::outputToWizard=FALSE;
QDict
<
int
>
*
Doxygen
::
htmlDirMap
=
0
;
QCache
<
LookupInfo
>
Doxygen
::
lookupCache
(
20000
,
20000
);
DirSDict
Doxygen
::
directories
(
17
);
SDict
<
DirRelation
>
Doxygen
::
dirRelations
(
257
);
static
StringList
inputFiles
;
static
StringDict
excludeNameDict
(
1009
);
// sections
...
...
@@ -4738,6 +4739,7 @@ static void findMember(Entry *root,
NamespaceSDict
::
Iterator
nsdi
(
*
nnl
);
for
(
nsdi
.
toFirst
();(
nnd
=
nsdi
.
current
());
++
nsdi
)
{
Debug
::
print
(
Debug
::
FindMembers
,
0
,
" adding used namespace %s
\n
"
,
nnd
->
qualifiedName
().
data
());
nl
->
append
(
nnd
->
qualifiedName
(),
nnd
);
}
}
...
...
@@ -4751,6 +4753,7 @@ static void findMember(Entry *root,
NamespaceSDict
::
Iterator
nsdi
(
*
fnl
);
for
(
nsdi
.
toFirst
();(
fnd
=
nsdi
.
current
());
++
nsdi
)
{
Debug
::
print
(
Debug
::
FindMembers
,
0
,
" adding used namespace %s
\n
"
,
fnd
->
qualifiedName
().
data
());
nl
->
append
(
fnd
->
qualifiedName
(),
fnd
);
}
}
...
...
@@ -4766,6 +4769,7 @@ static void findMember(Entry *root,
Definition
*
ncd
;
for
(
csdi
.
toFirst
();(
ncd
=
csdi
.
current
());
++
csdi
)
{
Debug
::
print
(
Debug
::
FindMembers
,
0
,
" adding used class %s
\n
"
,
ncd
->
qualifiedName
().
data
());
cl
->
append
(
ncd
->
qualifiedName
(),
ncd
);
}
}
...
...
@@ -4779,6 +4783,7 @@ static void findMember(Entry *root,
Definition
*
fcd
;
for
(
csdi
.
toFirst
();(
fcd
=
csdi
.
current
());
++
csdi
)
{
Debug
::
print
(
Debug
::
FindMembers
,
0
,
" adding used class %s
\n
"
,
fcd
->
qualifiedName
().
data
());
cl
->
append
(
fcd
->
qualifiedName
(),
fcd
);
}
}
...
...
@@ -7330,10 +7335,7 @@ static void readFiles(BufStr &output)
bufPtr
->
addChar
(
'\n'
);
/* to prevent problems under Windows ? */
//if (!multiLineIsBrief)
//{
convertCppComments
(
&
tempBuf
,
&
output
);
//}
convertCppComments
(
&
tempBuf
,
&
output
,
fileName
);
s
=
inputFiles
.
next
();
//printf("-------> adding new line\n");
...
...
@@ -7552,6 +7554,126 @@ static void readFormulaRepository()
}
}
//----------------------------------------------------------------------------
static
QDict
<
void
>
aliasesProcessed
;
static
QCString
expandAliasesRec
(
const
QCString
s
)
{
QCString
result
;
static
QRegExp
cmdPat
(
"[
\\\\
@][a-z_A-Z][a-z_A-Z0-9]*"
);
QCString
value
=
s
;
int
i
,
p
=
0
,
l
;
while
((
i
=
cmdPat
.
match
(
value
,
p
,
&
l
))
!=-
1
)
{
result
+=
value
.
mid
(
p
,
i
-
p
);
QCString
cmd
=
value
.
mid
(
i
+
1
,
l
-
1
);
//printf("Found command '%s'\n",cmd.data());
QCString
*
aliasText
=
Doxygen
::
aliasDict
.
find
(
cmd
);
if
(
aliasesProcessed
.
find
(
cmd
)
==
0
&&
aliasText
)
// expand the alias
{
aliasesProcessed
.
insert
(
cmd
,(
void
*
)
0x8
);
result
+=
expandAliasesRec
(
*
aliasText
);
aliasesProcessed
.
remove
(
cmd
);
}
else
// command is not an alias
{
result
+=
value
.
mid
(
i
,
l
);
}
p
=
i
+
l
;
}
result
+=
value
.
right
(
value
.
length
()
-
p
);
//printf("expandAliases '%s'->'%s'\n",s.data(),result.data());
return
result
;
}
static
void
expandAliases
()
{
QDictIterator
<
QCString
>
adi
(
Doxygen
::
aliasDict
);
QCString
*
s
;
for
(
adi
.
toFirst
();(
s
=
adi
.
current
());
++
adi
)
{
aliasesProcessed
.
clear
();
*
s
=
expandAliasesRec
(
*
s
);
}
}
//----------------------------------------------------------------------------
static
void
escapeAliases
()
{
QDictIterator
<
QCString
>
adi
(
Doxygen
::
aliasDict
);
QCString
*
s
;
for
(
adi
.
toFirst
();(
s
=
adi
.
current
());
++
adi
)
{
QCString
value
=*
s
,
newValue
;
int
in
,
p
=
0
;
// for each \n in the alias command value
while
((
in
=
value
.
find
(
"
\\
n"
,
p
))
!=-
1
)
{
newValue
+=
value
.
mid
(
p
,
in
-
p
);
// expand \n's except if \n is part of a built-in command.
if
(
value
.
mid
(
in
,
5
)
!=
"
\\
note"
&&
value
.
mid
(
in
,
5
)
!=
"
\\
name"
&&
value
.
mid
(
in
,
10
)
!=
"
\\
namespace"
&&
value
.
mid
(
in
,
14
)
!=
"
\\
nosubgrouping"
)
{
newValue
+=
"
\\
_linebr "
;
}
else
{
newValue
+=
"
\\
n"
;
}
p
=
in
+
2
;
}
newValue
+=
value
.
mid
(
p
,
value
.
length
()
-
p
);
*
s
=
newValue
;
//printf("Alias %s has value %s\n",adi.currentKey().data(),s->data());
}
}
//----------------------------------------------------------------------------
static
void
readAliases
()
{
// add aliases to a dictionary
Doxygen
::
aliasDict
.
setAutoDelete
(
TRUE
);
QStrList
&
aliasList
=
Config_getList
(
"ALIASES"
);
const
char
*
s
=
aliasList
.
first
();
while
(
s
)
{
if
(
Doxygen
::
aliasDict
[
s
]
==
0
)
{
QCString
alias
=
s
;
int
i
=
alias
.
find
(
'='
);
if
(
i
>
0
)
{
QCString
name
=
alias
.
left
(
i
).
stripWhiteSpace
();
QCString
value
=
alias
.
right
(
alias
.
length
()
-
i
-
1
);
//printf("Alias: found name=`%s' value=`%s'\n",name.data(),value.data());
if
(
!
name
.
isEmpty
())
{
QCString
*
dn
=
Doxygen
::
aliasDict
[
name
];
if
(
dn
==
0
)
// insert new alias
{
Doxygen
::
aliasDict
.
insert
(
name
,
new
QCString
(
value
));
}
else
// overwrite previous alias
{
*
dn
=
value
;
}
}
}
}
s
=
aliasList
.
next
();
}
expandAliases
();
escapeAliases
();
aliasesProcessed
.
clear
();
}
//----------------------------------------------------------------------------
// print the usage of doxygen
...
...
@@ -7620,6 +7742,8 @@ void initDoxygen()
Doxygen
::
memGrpInfoDict
.
setAutoDelete
(
TRUE
);
Doxygen
::
tagDestinationDict
.
setAutoDelete
(
TRUE
);
Doxygen
::
lookupCache
.
setAutoDelete
(
TRUE
);
Doxygen
::
directories
.
setAutoDelete
(
TRUE
);
Doxygen
::
dirRelations
.
setAutoDelete
(
TRUE
);
}
void
cleanUpDoxygen
()
...
...
@@ -8088,60 +8212,8 @@ void parseInput()
s
=
expandAsDefinedList
.
next
();
}
// add aliases to a dictionary
Doxygen
::
aliasDict
.
setAutoDelete
(
TRUE
);
QStrList
&
aliasList
=
Config_getList
(
"ALIASES"
);
s
=
aliasList
.
first
();
while
(
s
)
{
if
(
Doxygen
::
aliasDict
[
s
]
==
0
)
{
QCString
alias
=
s
;
int
i
=
alias
.
find
(
'='
);
if
(
i
>
0
)
{
QCString
name
=
alias
.
left
(
i
).
stripWhiteSpace
();
QCString
value
=
alias
.
right
(
alias
.
length
()
-
i
-
1
);
QCString
newValue
;
int
in
,
p
=
0
;
// for each \n in the alias command value
while
((
in
=
value
.
find
(
"
\\
n"
,
p
))
!=-
1
)
{
newValue
+=
value
.
mid
(
p
,
in
-
p
);
// expand \n's except if \n is part of a built-in command.
if
(
value
.
mid
(
in
,
5
)
!=
"
\\
note"
&&
value
.
mid
(
in
,
5
)
!=
"
\\
name"
&&
value
.
mid
(
in
,
10
)
!=
"
\\
namespace"
&&
value
.
mid
(
in
,
14
)
!=
"
\\
nosubgrouping"
)
{
newValue
+=
"
\n
"
;
}
else
{
newValue
+=
"
\\
n"
;
}
p
=
in
+
2
;
}
newValue
+=
value
.
mid
(
p
,
value
.
length
()
-
p
);
value
=
newValue
;
//printf("Alias: found name=`%s' value=`%s'\n",name.data(),value.data());
if
(
!
name
.
isEmpty
())
{
QCString
*
dn
=
Doxygen
::
aliasDict
[
name
];
if
(
dn
==
0
)
// insert new alias
{
Doxygen
::
aliasDict
.
insert
(
name
,
new
QCString
(
value
));
}
else
// overwrite previous alias
{
*
dn
=
value
;
}
}
}
}
s
=
aliasList
.
next
();
}
// read aliases and store them in a dictionary
readAliases
();
/**************************************************************************
* Handle Tag Files *
...
...
@@ -8448,8 +8520,11 @@ void parseInput()
msg
(
"Adding todo/test/bug list items...
\n
"
);
addListReferences
();
if
(
Config_getBool
(
"SHOW_DIRECTORIES"
))
{
msg
(
"Computing dependencies between directories...
\n
"
);
computeDirDependencies
();
}
}
void
generateOutput
()
...
...
src/doxygen.h
View file @
05930245
...
...
@@ -115,6 +115,7 @@ class Doxygen
static
QDict
<
int
>
*
htmlDirMap
;
static
QCache
<
LookupInfo
>
lookupCache
;
static
DirSDict
directories
;
static
SDict
<
DirRelation
>
dirRelations
;
};
void
initDoxygen
();
...
...
src/htmlgen.cpp
View file @
05930245
...
...
@@ -319,8 +319,16 @@ static const char *defaultStyleSheet =
"}
\n
"
"a:visited {
\n
"
" color: #3D2185;
\n
"
"}
\n
"
".dirtab { padding: 4px;
\n
"
" border-collapse: collapse;
\n
"
" border: 1px solid #b0b0b0;
\n
"
"}
\n
"
"TH.dirtab { background: #eeeeff;
\n
"
" font-weight: bold;
\n
"
"}
\n
"
;
static
QCString
g_header
;
static
QCString
g_footer
;
...
...
@@ -1246,6 +1254,15 @@ void HtmlGenerator::endCallGraph(DotCallGraph &g)
g
.
writeGraph
(
t
,
BITMAP
,
dir
,
relPath
);
}
void
HtmlGenerator
::
startDirDepGraph
()
{
}
void
HtmlGenerator
::
endDirDepGraph
(
DotDirDeps
&
g
)
{
g
.
writeGraph
(
t
,
BITMAP
,
dir
,
relPath
);
}
void
HtmlGenerator
::
writeGraphicalHierarchy
(
DotGfxHierarchyTable
&
g
)
{
g
.
writeGraph
(
t
,
dir
);
...
...
src/htmlgen.h
View file @
05930245
...
...
@@ -192,6 +192,8 @@ class HtmlGenerator : public OutputGenerator
void
endInclDepGraph
(
DotInclDepGraph
&
g
);
void
startCallGraph
();
void
endCallGraph
(
DotCallGraph
&
g
);
void
startDirDepGraph
();
void
endDirDepGraph
(
DotDirDeps
&
g
);
void
writeGraphicalHierarchy
(
DotGfxHierarchyTable
&
g
);
void
startTextBlock
(
bool
)
{}
...
...
src/htmlhelp.cpp
View file @
05930245
...
...
@@ -175,6 +175,26 @@ void HtmlHelpIndex::writeFields(QTextStream &t)
if
(
level2Started
)
t
<<
" </UL>"
<<
endl
;
level2Started
=
FALSE
;
// <Antony>
// Added this code so that an item with only one subitem is written
// without any subitem.
// For example:
// a1, b1 -> will create only a1, not separate subitem for b1
// a2, b2
// a2, b3
QCString
nextLevel1
;
IndexField
*
fnext
=
++
ifli
;
if
(
fnext
)
{
nextLevel1
=
fnext
->
name
.
left
(
fnext
->
name
.
find
(
'?'
));
--
ifli
;
}
if
(
level1
!=
nextLevel1
)
{
level2
=
""
;
}
// </Antony>
if
(
level2
.
isEmpty
())
{
t
<<
" <LI><OBJECT type=
\"
text/sitemap
\"
>"
;
...
...
@@ -189,7 +209,9 @@ void HtmlHelpIndex::writeFields(QTextStream &t)
if
(
f
->
link
)
{
t
<<
" <LI><OBJECT type=
\"
text/sitemap
\"
>"
;
t
<<
"<param name=
\"
Local
\"
value=
\"
"
<<
f
->
url
<<
Doxygen
::
htmlFileExtension
<<
"
\"
>"
;
t
<<
"<param name=
\"
Local
\"
value=
\"
"
<<
f
->
url
<<
Doxygen
::
htmlFileExtension
;
if
(
!
f
->
anchor
.
isEmpty
())
t
<<
"#"
<<
f
->
anchor
;
t
<<
"
\"
>"
;
t
<<
"<param name=
\"
Name
\"
value=
\"
"
<<
level1
<<
"
\"
>"
"</OBJECT>
\n
"
;
}
...
...
@@ -530,6 +552,6 @@ void HtmlHelp::addIndexItem(const char *level1, const char *level2,
const
char
*
ref
,
const
char
*
anchor
)
{
index
->
addItem
(
level1
,
level2
,
ref
,
anchor
,
TRUE
);
index
->
addItem
(
level2
,
level1
,
ref
,
anchor
,
FALS
E
);
index
->
addItem
(
level2
,
level1
,
ref
,
anchor
,
TRU
E
);
}
src/latexgen.cpp
View file @
05930245
...
...
@@ -1457,6 +1457,15 @@ void LatexGenerator::endCallGraph(DotCallGraph &g)
g
.
writeGraph
(
t
,
EPS
,
Config_getString
(
"LATEX_OUTPUT"
),
relPath
);
}
void
LatexGenerator
::
startDirDepGraph
()
{
}
void
LatexGenerator
::
endDirDepGraph
(
DotDirDeps
&
g
)
{
g
.
writeGraph
(
t
,
EPS
,
Config_getString
(
"LATEX_OUTPUT"
),
relPath
);
}
void
LatexGenerator
::
startDescription
()
{
t
<<
"
\\
begin{description}"
<<
endl
;
...
...
src/latexgen.h
View file @
05930245
...
...
@@ -185,6 +185,8 @@ class LatexGenerator : public OutputGenerator
void
endInclDepGraph
(
DotInclDepGraph
&
);
void
startCallGraph
();
void
endCallGraph
(
DotCallGraph
&
);
void
startDirDepGraph
();
void
endDirDepGraph
(
DotDirDeps
&
g
);
void
writeGraphicalHierarchy
(
DotGfxHierarchyTable
&
)
{}
void
startTextBlock
(
bool
)
{}
...
...
src/mangen.h
View file @
05930245
...
...
@@ -231,6 +231,8 @@ class ManGenerator : public OutputGenerator
void
endInclDepGraph
(
DotInclDepGraph
&
)
{}
void
startCallGraph
()
{}
void
endCallGraph
(
DotCallGraph
&
)
{}
void
startDirDepGraph
()
{}
void
endDirDepGraph
(
DotDirDeps
&
)
{}
void
writeGraphicalHierarchy
(
DotGfxHierarchyTable
&
)
{}
void
startTextBlock
(
bool
)
{}
...
...
src/outputgen.h
View file @
05930245
...
...
@@ -30,6 +30,7 @@ class ClassDiagram;
class
DotClassGraph
;
class
DotInclDepGraph
;
class
DotCallGraph
;
class
DotDirDeps
;
class
DotGfxHierarchyTable
;
class
DocNode
;
class
MemberDef
;
...
...
@@ -339,6 +340,8 @@ class OutputGenerator : public BaseOutputDocInterface
virtual
void
endInclDepGraph
(
DotInclDepGraph
&
g
)
=
0
;
virtual
void
startCallGraph
()
=
0
;
virtual
void
endCallGraph
(
DotCallGraph
&
g
)
=
0
;
virtual
void
startDirDepGraph
()
=
0
;
virtual
void
endDirDepGraph
(
DotDirDeps
&
g
)
=
0
;
virtual
void
writeGraphicalHierarchy
(
DotGfxHierarchyTable
&
g
)
=
0
;
//virtual void startQuickIndexItem(const char *s,const char *l) = 0;
//virtual void endQuickIndexItem() = 0;
...
...
src/outputlist.cpp
View file @
05930245
...
...
@@ -266,6 +266,7 @@ FORALL1(int a1,a1)
FORALL1
(
DotClassGraph
&
a1
,
a1
)
FORALL1
(
DotInclDepGraph
&
a1
,
a1
)
FORALL1
(
DotCallGraph
&
a1
,
a1
)
FORALL1
(
DotDirDeps
&
a1
,
a1
)
FORALL1
(
DotGfxHierarchyTable
&
a1
,
a1
)
FORALL1
(
SectionTypes
a1
,
a1
)
#if defined(HAS_BOOL_TYPE) || defined(Q_HAS_BOOL_TYPE)
...
...
src/outputlist.h
View file @
05930245
...
...
@@ -34,6 +34,7 @@
class
ClassDiagram
;
class
DotClassGraph
;
class
DotDirDeps
;
class
DotInclDepGraph
;
class
DotGfxHierarchyTable
;
class
SectionDict
;
...
...
@@ -322,6 +323,10 @@ class OutputList : public OutputDocInterface
{
forall
(
&
OutputGenerator
::
startCallGraph
);
}
void
endCallGraph
(
DotCallGraph
&
g
)
{
forall
(
&
OutputGenerator
::
endCallGraph
,
g
);
}
void
startDirDepGraph
()
{
forall
(
&
OutputGenerator
::
startDirDepGraph
);
}
void
endDirDepGraph
(
DotDirDeps
&
g
)
{
forall
(
&
OutputGenerator
::
endDirDepGraph
,
g
);
}
void
writeGraphicalHierarchy
(
DotGfxHierarchyTable
&
g
)
{
forall
(
&
OutputGenerator
::
writeGraphicalHierarchy
,
g
);
}
void
startTextBlock
(
bool
dense
=
FALSE
)
...
...
@@ -387,6 +392,7 @@ class OutputList : public OutputDocInterface
FORALLPROTO1
(
DotClassGraph
&
);
FORALLPROTO1
(
DotInclDepGraph
&
);
FORALLPROTO1
(
DotCallGraph
&
);
FORALLPROTO1
(
DotDirDeps
&
);
FORALLPROTO1
(
DotGfxHierarchyTable
&
);
FORALLPROTO1
(
SectionTypes
);
#if defined(HAS_BOOL_TYPE) || defined(Q_HAS_BOOL_TYPE)
...
...
src/pre.l
View file @
05930245
...
...
@@ -1079,7 +1079,7 @@ static void readIncludeFile(const QCString &inc)
if (g_yyFileDef)
{
//printf("Adding include dependency %s->%s\n",oldFileDef->name().data(),incFileName.data());
g_yyFileDef->addIncludedByDependency(oldFileDef,oldFileDef->
n
ame(),localInclude,g_isImported);
g_yyFileDef->addIncludedByDependency(oldFileDef,oldFileDef->
docN
ame(),localInclude,g_isImported);
}
}
FileState *fs=new FileState;
...
...
@@ -1114,7 +1114,7 @@ static void readIncludeFile(const QCString &inc)
if (fd)
{
//printf("Adding include dependency (2) %s->%s ambig=%d\n",oldFileDef->name().data(),fd->name().data(),ambig);
fd->addIncludedByDependency(oldFileDef,oldFileDef->
n
ame(),localInclude,g_isImported);
fd->addIncludedByDependency(oldFileDef,oldFileDef->
docN
ame(),localInclude,g_isImported);
}
}
if (Debug::isFlagSet(Debug::Preprocessor))
...
...
src/rtfgen.cpp
View file @
05930245
...
...
@@ -2258,6 +2258,28 @@ void RTFGenerator::endCallGraph(DotCallGraph &g)
DBG_RTF
(
t
<<
"{
\\
comment (endCallGraph)}"
<<
endl
)
}
void
RTFGenerator
::
startDirDepGraph
()
{
DBG_RTF
(
t
<<
"{
\\
comment (startDirDepGraph)}"
<<
endl
)
}
void
RTFGenerator
::
endDirDepGraph
(
DotDirDeps
&
g
)
{
newParagraph
();
QCString
fileName
=
g
.
writeGraph
(
t
,
BITMAP
,
Config_getString
(
"RTF_OUTPUT"
),
relPath
,
FALSE
);
// display the file
t
<<
"{"
<<
endl
;
t
<<
rtf_Style_Reset
<<
endl
;
t
<<
"
\\
par
\\
pard
\\
qc {
\\
field
\\
flddirty {
\\
*
\\
fldinst INCLUDEPICTURE
\"
"
;
t
<<
fileName
<<
"."
<<
Config_getEnum
(
"DOT_IMAGE_FORMAT"
);
t
<<
"
\"
\\\\
d
\\\\
*MERGEFORMAT}{
\\
fldrslt IMAGE}}
\\
par"
<<
endl
;
t
<<
"}"
<<
endl
;
DBG_RTF
(
t
<<
"{
\\
comment (endDirDepGraph)}"
<<
endl
)
}
/** Tests the integrity of the result by counting brackets.
*
*/
...
...
src/rtfgen.h
View file @
05930245
...
...
@@ -227,6 +227,8 @@ class RTFGenerator : public OutputGenerator
void
endInclDepGraph
(
DotInclDepGraph
&
);
void
startCallGraph
();
void
endCallGraph
(
DotCallGraph
&
);
void
startDirDepGraph
();
void
endDirDepGraph
(
DotDirDeps
&
g
);
void
writeGraphicalHierarchy
(
DotGfxHierarchyTable
&
)
{}
void
startMemberGroupHeader
(
bool
);
...
...
src/scanner.l
View file @
05930245
...
...
@@ -5612,6 +5612,10 @@ PHPKW ("require"|"require_once"|"include"|"include_once"|"echo")[^a-zA-Z0-9_;]
unput('/');unput('*');
BEGIN( tmpDocType );
}
<Doc,JavaDoc,LineDoc,ClassDocBrief,AfterDocBrief,AfterDocLine,CopyArgCommentLine,ClassDoc,PageDoc,AfterDoc,CopyArgComment>"\\_linebr " {
// used to compensate for misalignments due to \n's inside ALIASES
current->doc += '\n';
}
<Doc,JavaDoc,ClassDoc,PageDoc,ReadFormulaShort,ReadFormulaLong,AfterDoc>^{B}*(("//"{B}*)?)"*"+[ \t]*"-"("#")?{B}+ {
current->doc += yytext;
}
...
...
src/sortdict.h
View file @
05930245
...
...
@@ -234,7 +234,7 @@ class SDict
/*! Returns the number of items stored in the dictionary
*/
int
count
()
int
count
()
const
{
return
m_list
->
count
();
}
...
...
src/util.cpp
View file @
05930245
...
...
@@ -45,6 +45,7 @@
#include "groupdef.h"
#include "reflist.h"
#include "pagedef.h"
#include "debug.h"
#if !defined(_WIN32) || defined(__CYGWIN__)
#include <unistd.h>
...
...
@@ -140,7 +141,7 @@ int iSystem(const char *command,const char *args,bool isBatchFile)
}
fullCmd
+=
" "
;
fullCmd
+=
args
;
//printf("iSystem: Executing %s
\n",fullCmd.data());
Debug
::
print
(
Debug
::
ExtCmd
,
0
,
"Executing external command
\"
%s
\"
\n
"
,
fullCmd
.
data
());
#if !defined(_WIN32) || defined(__CYGWIN__)
isBatchFile
=
isBatchFile
;
...
...
@@ -2597,6 +2598,172 @@ bool matchArguments(ArgumentList *srcAl,ArgumentList *dstAl,
return
TRUE
;
// all arguments match
}
static
QCString
extractCanonicalType
(
Definition
*
d
,
FileDef
*
fs
,
const
Argument
*
arg
)
{
QCString
type
=
arg
->
type
;
QCString
name
=
arg
->
name
;
if
((
type
==
"const"
||
type
==
"volatile"
)
&&
!
name
.
isEmpty
())
{
// name is part of type => correct
type
+=
" "
;
type
+=
name
;
}
if
(
name
==
"const"
||
name
==
"volatile"
)
{
// name is part of type => correct
if
(
!
type
.
isEmpty
())
type
+=
" "
;
type
+=
name
;
}
// strip const and volatile keywords that are not relatevant for the type
stripIrrelevantConstVolatile
(
type
);
// strip leading keywords
if
(
type
.
left
(
6
)
==
"class "
)
type
=
type
.
right
(
type
.
length
()
-
6
);
else
if
(
type
.
left
(
7
)
==
"struct "
)
type
=
type
.
right
(
type
.
length
()
-
7
);
else
if
(
type
.
left
(
6
)
==
"union "
)
type
=
type
.
right
(
type
.
length
()
-
6
);
else
if
(
type
.
left
(
5
)
==
"enum "
)
type
=
type
.
right
(
type
.
length
()
-
5
);
else
if
(
type
.
left
(
9
)
==
"typename "
)
type
=
type
.
right
(
type
.
length
()
-
9
);
static
QRegExp
id
(
"[a-z_A-Z][a-z_A-Z0-9]*"
);
QCString
canType
;
int
i
,
p
=
0
,
l
;
while
((
i
=
id
.
match
(
type
,
p
,
&
l
)))
// foreach identifier in the type
{
canType
+=
type
.
mid
(
p
,
i
-
p
);
QCString
word
=
type
.
mid
(
i
,
l
);
ClassDef
*
cd
=
getResolvedClass
(
d
,
fs
,
word
);
if
(
cd
)
{
canType
+=
cd
->
qualifiedName
();
}
else
{
canType
+=
word
;
}
p
=
i
+
l
;
}
canType
+=
type
.
right
(
type
.
length
()
-
p
);
return
removeRedundantWhiteSpace
(
canType
);
}
static
bool
matchArgument2
(
Definition
*
srcScope
,
FileDef
*
srcFileScope
,
const
Argument
*
srcA
,
Definition
*
dstScope
,
FileDef
*
dstFileScope
,
const
Argument
*
dstA
)
{
//printf("match argument start `%s|%s' <-> `%s|%s' using nsp=%p class=%p\n",
// srcA->type.data(),srcA->name.data(),
// dstA->type.data(),dstA->name.data(),
// usingNamespaces,
// usingClasses);
if
(
srcA
->
array
!=
dstA
->
array
)
// nomatch for char[] against char
{
NOMATCH
return
FALSE
;
}
QCString
canonicalSrcType
=
extractCanonicalType
(
srcScope
,
srcFileScope
,
srcA
);
QCString
canonicalDstType
=
extractCanonicalType
(
dstScope
,
dstFileScope
,
dstA
);
if
(
canonicalSrcType
==
canonicalDstType
)
{
MATCH
return
TRUE
;
}
else
{
NOMATCH
return
FALSE
;
}
}
// new algorithm for argument matching
bool
matchArguments2
(
Definition
*
srcScope
,
FileDef
*
srcFileScope
,
ArgumentList
*
srcAl
,
Definition
*
dstScope
,
FileDef
*
dstFileScope
,
ArgumentList
*
dstAl
,
bool
checkCV
)
{
ASSERT
(
srcScope
!=
0
&&
dstScope
!=
0
);
if
(
srcAl
==
0
||
dstAl
==
0
)
{
bool
match
=
srcAl
==
dstAl
;
// at least one of the members is not a function
if
(
match
)
{
MATCH
return
TRUE
;
}
else
{
NOMATCH
return
FALSE
;
}
}
// handle special case with void argument
if
(
srcAl
->
count
()
==
0
&&
dstAl
->
count
()
==
1
&&
dstAl
->
getFirst
()
->
type
==
"void"
)
{
// special case for finding match between func() and func(void)
Argument
*
a
=
new
Argument
;
a
->
type
=
"void"
;
srcAl
->
append
(
a
);
MATCH
return
TRUE
;
}
if
(
dstAl
->
count
()
==
0
&&
srcAl
->
count
()
==
1
&&
srcAl
->
getFirst
()
->
type
==
"void"
)
{
// special case for finding match between func(void) and func()
Argument
*
a
=
new
Argument
;
a
->
type
=
"void"
;
dstAl
->
append
(
a
);
MATCH
return
TRUE
;
}
if
(
srcAl
->
count
()
!=
dstAl
->
count
())
{
NOMATCH
return
FALSE
;
// different number of arguments -> no match
}
if
(
checkCV
)
{
if
(
srcAl
->
constSpecifier
!=
dstAl
->
constSpecifier
)
{
NOMATCH
return
FALSE
;
// one member is const, the other not -> no match
}
if
(
srcAl
->
volatileSpecifier
!=
dstAl
->
volatileSpecifier
)
{
NOMATCH
return
FALSE
;
// one member is volatile, the other not -> no match
}
}
// so far the argument list could match, so we need to compare the types of
// all arguments.
ArgumentListIterator
srcAli
(
*
srcAl
),
dstAli
(
*
dstAl
);
Argument
*
srcA
,
*
dstA
;
for
(;(
srcA
=
srcAli
.
current
(),
dstA
=
dstAli
.
current
());
++
srcAli
,
++
dstAli
)
{
if
(
!
matchArgument2
(
srcScope
,
srcFileScope
,
srcA
,
dstScope
,
dstFileScope
,
dstA
)
)
{
NOMATCH
return
FALSE
;
}
}
MATCH
return
TRUE
;
// all arguments match
}
// merges the initializer of two argument lists
// pre: the types of the arguments in the list should match.
void
mergeArguments
(
ArgumentList
*
srcAl
,
ArgumentList
*
dstAl
,
bool
forceNameOverwrite
)
...
...
@@ -2934,7 +3101,7 @@ bool getDefs(const QCString &scName,const QCString &memberName,
{
// namespace is found
bool
match
=
TRUE
;
ArgumentList
*
argList
=
0
;
if
(
args
)
if
(
args
&&
strcmp
(
args
,
"()"
)
!=
0
)
{
argList
=
new
ArgumentList
;
stringToArgumentList
(
args
,
argList
);
...
...
@@ -3001,10 +3168,10 @@ bool getDefs(const QCString &scName,const QCString &memberName,
(
gd
&&
gd
->
isLinkable
())
||
(
fd
&&
fd
->
isLinkable
())
)
{
//printf("
fd=%p gd=%p inGroup=`%d' args=`%s'\n",fd,gd,inGroup
,args);
//printf("
fd=%p gd=%p args=`%s'\n",fd,gd
,args);
bool
match
=
TRUE
;
ArgumentList
*
argList
=
0
;
if
(
args
&&
!
md
->
isDefine
())
if
(
args
&&
!
md
->
isDefine
()
&&
strcmp
(
args
,
"()"
)
!=
0
)
{
argList
=
new
ArgumentList
;
stringToArgumentList
(
args
,
argList
);
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment