summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/classdef.cpp2
-rw-r--r--src/code.l91
-rw-r--r--src/doxygen.cpp119
-rw-r--r--src/htmlgen.cpp95
-rw-r--r--src/htmlgen.h4
-rw-r--r--src/latexgen.h5
-rw-r--r--src/mangen.h5
-rw-r--r--src/memberdef.cpp29
-rw-r--r--src/outputgen.h4
-rw-r--r--src/outputlist.h8
-rw-r--r--src/rtfgen.h4
-rw-r--r--src/scanner.l56
-rw-r--r--src/util.cpp61
13 files changed, 370 insertions, 113 deletions
diff --git a/src/classdef.cpp b/src/classdef.cpp
index 3d5b4ce..b488214 100644
--- a/src/classdef.cpp
+++ b/src/classdef.cpp
@@ -1637,7 +1637,7 @@ void ClassDef::determineImplUsageRelation()
bool found=FALSE;
while ((i=re.match(type,p,&l))!=-1 && !found) // for each class name in the type
{
- int ts=p+l;
+ int ts=i+l;
int te=ts;
while (type.at(ts)==' ' && ts<typeLen) ts++; // skip any whitespace
if (type.at(ts)=='<') // assume template instance
diff --git a/src/code.l b/src/code.l
index 1a6b3f1..1fd0a91 100644
--- a/src/code.l
+++ b/src/code.l
@@ -284,10 +284,10 @@ static void generateClassLink(OutputList &ol,char *clName,int *clNameLen=0)
QCString className=clName;
if (clNameLen) *clNameLen=0;
if (className.isEmpty()) return;
- ClassDef *cd=getClass(className);
+ ClassDef *cd=getResolvedClass(className);
if (cd==0 && (i=className.find('<'))!=-1)
{
- cd=getClass(className.left(i));
+ cd=getResolvedClass(className.left(i));
}
if (cd && cd->isLinkable())
{
@@ -374,7 +374,7 @@ static ClassDef *stripClassName(const char *s)
int p=0,i,l;
while ((i=re.match(tmp,p,&l))!=-1)
{
- ClassDef *cd=getClass(tmp.mid(i,l));
+ ClassDef *cd=getResolvedClass(tmp.mid(i,l));
if (cd) return cd;
p=i+l;
}
@@ -579,8 +579,10 @@ B [ \t]
BN [ \t\n\r]
ID [a-z_A-Z][a-z_A-Z0-9]*
SCOPENAME (({ID}?{BN}*"::"{BN}*)*)((~{BN}*)?{ID})
-KEYWORD ("asm"|"auto"|"break"|"case"|"catch"|"class"|"const_cast"|"continue"|"default"|"delete"|"do"|"dynamic_cast"|"else"|"enum"|"explicit"|"extern"|"false"|"for"|"friend"|"goto"|"if"|"inline"|"mutable"|"namespace"|"new"|"operator"|"private"|"protected"|"public"|"register"|"reinterpret_cast"|"return"|"sizeof"|"static"|"static_cast"|"struct"|"switch"|"template"|"this"|"throw"|"true"|"try"|"typedef"|"typeid"|"typename"|"union"|"using"|"virtual"|"volatile"|"while")
-TYPEKW ("bool"|"char"|"const"|"double"|"float"|"int"|"long"|"short"|"signed"|"unsigned"|"void"|"wchar_t")
+SCOPEPREFIX {ID}{B}*"::"({B}*{ID}{B}*"::")*
+KEYWORD ("asm"|"auto"|"class"|"const"|"const_cast"|"delete"|"dynamic_cast"|"enum"|"explicit"|"extern"|"false"|"friend"|"inline"|"mutable"|"namespace"|"new"|"operator"|"private"|"protected"|"public"|"register"|"reinterpret_cast"|"sizeof"|"static"|"static_cast"|"struct"|"template"|"this"|"true"|"typedef"|"typeid"|"typename"|"union"|"using"|"virtual"|"volatile")
+FLOWKW ("break"|"case"|"catch"|"continue"|"default"|"do"|"else"|"for"|"goto"|"if"|"return"|"switch"|"throw"|"try"|"while")
+TYPEKW ("bool"|"char"|"double"|"float"|"int"|"long"|"short"|"signed"|"unsigned"|"void"|"wchar_t")
%option noyywrap
@@ -603,7 +605,7 @@ TYPEKW ("bool"|"char"|"const"|"double"|"float"|"int"|"long"|"short"|"signed"|"u
%%
<*>\x0d
-<Body>^([ \t]*"#"[ \t]"include"[ \t]*)("<"|"\"") {
+<Body>^([ \t]*"#"[ \t]*"include"[ \t]*)("<"|"\"") {
startFontClass("preprocessor");
g_code->codify(yytext);
BEGIN( ReadInclude );
@@ -728,22 +730,54 @@ TYPEKW ("bool"|"char"|"const"|"double"|"float"|"int"|"long"|"short"|"signed"|"u
}
-<Body>{KEYWORD}/([^a-z_A-Z0-9]) {
+<Body>{SCOPEPREFIX}*{B}*"operator"{B}*"()"{B}*/"(" {
+ addType();
+ generateFunctionLink(*g_code,yytext);
+ g_bracketCount=1;
+ g_args.resize(0);
+ g_name+=yytext;
+ BEGIN( FuncCall );
+ }
+<Body>{SCOPEPREFIX}*{B}*"operator"{B}*[^\(\n]+/"(" {
+ addType();
+ generateFunctionLink(*g_code,yytext);
+ g_bracketCount=1;
+ g_args.resize(0);
+ g_name+=yytext;
+ BEGIN( FuncCall );
+ }
+<Body>{KEYWORD}/([^a-z_A-Z0-9]) {
startFontClass("keyword");
codifyLines(yytext);
endFontClass();
}
-<Body>{KEYWORD}/{B}* {
+<Body>{KEYWORD}/{B}* {
startFontClass("keyword");
codifyLines(yytext);
endFontClass();
}
-<Body>{KEYWORD}/{B}*"(" {
+<Body>{KEYWORD}/{B}*"(" {
startFontClass("keyword");
codifyLines(yytext);
endFontClass();
g_name.resize(0);g_type.resize(0);
}
+<Body>{FLOWKW}/([^a-z_A-Z0-9]) {
+ startFontClass("keywordflow");
+ codifyLines(yytext);
+ endFontClass();
+ }
+<Body>{FLOWKW}/{B}* {
+ startFontClass("keywordflow");
+ codifyLines(yytext);
+ endFontClass();
+ }
+<Body>{FLOWKW}/{B}*"(" {
+ startFontClass("keywordflow");
+ codifyLines(yytext);
+ endFontClass();
+ g_name.resize(0);g_type.resize(0);
+ }
<Body>[\\|\)\+\-\/\%\~\!] {
g_code->codify(yytext);
g_name.resize(0);g_type.resize(0);
@@ -756,13 +790,13 @@ TYPEKW ("bool"|"char"|"const"|"double"|"float"|"int"|"long"|"short"|"signed"|"u
}
*/
<Body>{TYPEKW}/{B}* {
- startFontClass("keyword");
+ startFontClass("keywordtype");
g_code->codify(yytext);
endFontClass();
addType();
g_name+=yytext;
}
-<Body>{SCOPENAME}{B}*"<"[^\}\{\(\)\/\n\>]*">"/{B}* {
+<Body>{SCOPENAME}{B}*"<"[^\"\}\{\(\)\/\n\>]*">"/{B}* {
int i;
generateClassLink(*g_code,yytext,&i);
addType();
@@ -771,23 +805,19 @@ TYPEKW ("bool"|"char"|"const"|"double"|"float"|"int"|"long"|"short"|"signed"|"u
}
<Body>{SCOPENAME}/{B}* {
generateClassLink(*g_code,yytext);
- //codifyLines(yytext);
addType();
g_name+=yytext;
}
<Body>{SCOPENAME}/{B}*"(" {
addType();
- //if (type.isEmpty())
- QCString tmp=yytext;
generateFunctionLink(*g_code,yytext);
- //else
- // g_code->codify(yytext);
g_bracketCount=1;
g_args.resize(0);
g_name+=yytext;
BEGIN( FuncCall );
}
<FuncCall,Body,MemberCall>\" {
+ startFontClass("stringliteral");
g_code->codify(yytext);
g_lastStringContext=YY_START;
BEGIN( SkipString );
@@ -800,6 +830,7 @@ TYPEKW ("bool"|"char"|"const"|"double"|"float"|"int"|"long"|"short"|"signed"|"u
}
<SkipString>\" {
g_code->codify(yytext);
+ endFontClass();
BEGIN( g_lastStringContext );
}
<SkipString>\\. {
@@ -809,8 +840,10 @@ TYPEKW ("bool"|"char"|"const"|"double"|"float"|"int"|"long"|"short"|"signed"|"u
g_code->codify(yytext);
g_name.resize(0);g_type.resize(0);
}
-<Body,MemberCall,MemberCall2,FuncCall>"'"((\\.)|(.))"'" {
+<Body,MemberCall,MemberCall2,FuncCall>"'"((\\0[Xx0-9]+)|(\\.)|(.))"'" {
+ startFontClass("charliteral");
g_code->codify(yytext);
+ endFontClass();
}
<Body>"this->" { g_code->codify(yytext); }
<Body>"."|"->" {
@@ -843,13 +876,27 @@ TYPEKW ("bool"|"char"|"const"|"double"|"float"|"int"|"long"|"short"|"signed"|"u
<Body>[0-9]+ {
g_code->codify(yytext);
}
-<MemberCall2,FuncCall>({KEYWORD}|{TYPEKW})/([^a-z_A-Z0-9]) {
+<MemberCall2,FuncCall>{KEYWORD}/([^a-z_A-Z0-9]) {
addParmType();
g_parmName=yytext;
startFontClass("keyword");
g_code->codify(yytext);
endFontClass();
}
+<MemberCall2,FuncCall>{TYPEKW}/([^a-z_A-Z0-9]) {
+ addParmType();
+ g_parmName=yytext;
+ startFontClass("keywordtype");
+ g_code->codify(yytext);
+ endFontClass();
+ }
+<MemberCall2,FuncCall>{FLOWKW}/([^a-z_A-Z0-9]) {
+ addParmType();
+ g_parmName=yytext;
+ startFontClass("keywordflow");
+ g_code->codify(yytext);
+ endFontClass();
+ }
<MemberCall2,FuncCall>[a-z_A-Z][:a-z_A-Z0-9]* {
addParmType();
g_parmName=yytext;
@@ -943,7 +990,7 @@ TYPEKW ("bool"|"char"|"const"|"double"|"float"|"int"|"long"|"short"|"signed"|"u
endFontClass();
BEGIN( g_lastCContext ) ;
}
-<SkipCxxComment>[^\r\n]* {
+<SkipCxxComment>[^\r\n]+ {
g_code->codify(yytext);
}
<SkipCxxComment>\r
@@ -1038,7 +1085,11 @@ TYPEKW ("bool"|"char"|"const"|"double"|"float"|"int"|"long"|"short"|"signed"|"u
}
else
{
- g_lastCContext = YY_START ;
+ // check is to prevent getting stuck in skipping C++ comments
+ if (YY_START != SkipCxxComment)
+ {
+ g_lastCContext = YY_START ;
+ }
startFontClass("comment");
codifyLines(yytext);
BEGIN(SkipComment);
diff --git a/src/doxygen.cpp b/src/doxygen.cpp
index c40a4da..40a21f8 100644
--- a/src/doxygen.cpp
+++ b/src/doxygen.cpp
@@ -154,7 +154,7 @@ int documentedIncludeFiles;
QTextStream tagFile;
void addMemberDocs(Entry *root,MemberDef *md, const char *funcDecl,
- bool over_load,NamespaceList *nl=0);
+ ArgumentList *al,bool over_load,NamespaceList *nl=0);
const char idMask[] = "[A-Za-z_][A-Za-z_0-9]*";
QCString spaces;
@@ -782,9 +782,16 @@ void findUsingDirectives(Entry *root)
//----------------------------------------------------------------------
-static MemberDef *addVariableToClass(Entry *root,ClassDef *cd,
- MemberDef::MemberType mtype,const QCString &scope,const QCString &name,
- bool fromAnnScope,int indentDepth,MemberDef *fromAnnMemb,Protection prot)
+static MemberDef *addVariableToClass(
+ Entry *root,
+ ClassDef *cd,
+ MemberDef::MemberType mtype,
+ const QCString &scope,
+ const QCString &name,
+ bool fromAnnScope,
+ int indentDepth,
+ MemberDef *fromAnnMemb,
+ Protection prot)
{
Debug::print(Debug::Variables,0,
" class variable:\n"
@@ -832,7 +839,7 @@ static MemberDef *addVariableToClass(Entry *root,ClassDef *cd,
if (md->memberClass()==cd && root->type==md->typeString())
// member already in the scope
{
- addMemberDocs(root,md,def,FALSE);
+ addMemberDocs(root,md,def,0,FALSE);
return md;
}
md=mn->next();
@@ -885,9 +892,14 @@ static MemberDef *addVariableToClass(Entry *root,ClassDef *cd,
//----------------------------------------------------------------------
-static MemberDef *addVariableToFile(Entry *root,MemberDef::MemberType mtype,
- const QCString &scope,const QCString &name,
- bool fromAnnScope,int indentDepth,MemberDef *fromAnnMemb)
+static MemberDef *addVariableToFile(
+ Entry *root,
+ MemberDef::MemberType mtype,
+ const QCString &scope,
+ const QCString &name,
+ bool fromAnnScope,
+ int indentDepth,
+ MemberDef *fromAnnMemb)
{
Debug::print(Debug::Variables,0,
" global variable:\n"
@@ -1134,7 +1146,8 @@ void buildVarList(Entry *root)
else // annonymous scope inside namespace or file => put variable in the global scope
{
//printf("Inserting member in global scope %s!\n",pScope.data());
- md=addVariableToFile(root,mtype,pScope,name,!pScope.isEmpty(),indentDepth,0);
+ //md=addVariableToFile(root,mtype,pScope,name,!pScope.isEmpty(),indentDepth,0);
+ md=addVariableToFile(root,mtype,pScope,name,TRUE,indentDepth,0);
}
}
}
@@ -1734,11 +1747,20 @@ static bool findBaseClassRelation(Entry *root,ClassDef *cd,
{
// TODO: here we should try to find the correct template specialization
// but for now, we only look for the unspecializated base class.
- int e = baseClassName.find('>');
- if (e!=-1)
+ // locate end of template
+ int e=i+1;
+ int brCount=1;
+ int typeLen = baseClassName.length();
+ while (e<typeLen && brCount!=0)
{
- templSpec=baseClassName.mid(i,e-i+1);
- baseClassName=baseClassName.left(i)+baseClassName.right(baseClassName.length()-e-1);
+ if (baseClassName.at(e)=='<') brCount++;
+ if (baseClassName.at(e)=='>') brCount--;
+ e++;
+ }
+ if (brCount==0) // end of template was found at e
+ {
+ templSpec=baseClassName.mid(i,e-i);
+ baseClassName=baseClassName.left(i)+baseClassName.right(baseClassName.length()-e);
baseClass=getResolvedClass(baseClassName);
//printf("baseClass=%p baseClass=%s templSpec=%s\n",
// baseClass,baseClassName.data(),templSpec.data());
@@ -1796,7 +1818,7 @@ static bool findBaseClassRelation(Entry *root,ClassDef *cd,
}
else if (insertUndocumented)
{
- Debug::print(Debug::Classes,0," Undocumented base class `%s'\n",bi->name.data());
+ Debug::print(Debug::Classes,0," Undocumented base class `%s' baseClassName=%s\n",bi->name.data(),baseClassName.data());
baseClass=new ClassDef(baseClassName,ClassDef::Class);
// add base class to this class
cd->insertBaseClass(baseClass,bi->prot,bi->virt,templSpec);
@@ -1947,8 +1969,12 @@ void computeMemberReferences()
// set the function declaration of the member to `funcDecl'. If the boolean
// over_load is set the standard overload text is added.
-void addMemberDocs(Entry *root,MemberDef *md, const char *funcDecl,
- bool over_load,NamespaceList *nl)
+void addMemberDocs(Entry *root,
+ MemberDef *md, const char *funcDecl,
+ ArgumentList *al,
+ bool over_load,
+ NamespaceList *nl
+ )
{
//printf("addMemberDocs: `%s'::`%s' `%s' funcDecl=`%s'\n",
// root->parent->name.data(),md->name().data(),md->argsString(),funcDecl);
@@ -1958,15 +1984,22 @@ void addMemberDocs(Entry *root,MemberDef *md, const char *funcDecl,
md->setDefinition(fDecl);
ClassDef *cd=md->memberClass();
NamespaceDef *nd=md->getNamespace();
- if (matchArguments(md->argumentList(),root->argList,
- cd ? cd->name().data() : 0,
- nd ? nd->name().data() : 0,
- TRUE,
- nl
- )
- )
+ if (al)
{
- mergeArguments(md->argumentList(),root->argList);
+ mergeArguments(md->argumentList(),al);
+ }
+ else
+ {
+ if (matchArguments(md->argumentList(),root->argList,
+ cd ? cd->name().data() : 0,
+ nd ? nd->name().data() : 0,
+ TRUE,
+ nl
+ )
+ )
+ {
+ mergeArguments(md->argumentList(),root->argList);
+ }
}
if (over_load) // the \overload keyword was used
{
@@ -2133,20 +2166,19 @@ static bool findUnrelatedFunction(Entry *root,
{
Debug::print(Debug::FindMembers,0,"4. Try to add member `%s' to scope `%s'\n",
md->name().data(),namespaceName.data());
- //printf("Searching for match between %s and %s\n",
- // argListToString(md->argumentList()).data(),
- // argListToString(root->argList).data());
+ //ArgumentList *al = new ArgumentList;
+ //stringToArgumentList(funcArgs,al);
QCString nsName = nd ? nd->name().data() : "";
bool matching=
- /*matchArguments(md->argsString(),args);*/
(md->argumentList()==0 && root->argList->count()==0) ||
matchArguments(md->argumentList(),root->argList,0,nsName);
if (matching) // add docs to the member
{
Debug::print(Debug::FindMembers,0,"5. Match found\n");
- addMemberDocs(root,md,decl,FALSE);
+ addMemberDocs(root,md,decl,root->argList,FALSE);
found=TRUE;
}
+ //delete al;
}
md=mn->next();
}
@@ -2468,7 +2500,6 @@ void findMember(Entry *root,QCString funcDecl,QCString related,bool overloaded,
}
}
-
if (root->tArgList==0 && !classTempList.isEmpty())
{
// no template specifiers found during parsing (because \fn was used),
@@ -2542,13 +2573,6 @@ void findMember(Entry *root,QCString funcDecl,QCString related,bool overloaded,
QCString fullFuncDecl=funcDecl.copy();
if (isFunc) fullFuncDecl+=argListToString(root->argList);
- // destructor => do backward class name substitution if needed
- //if (!funcName.isEmpty() && funcName[0]=='~')
- // funcName="~"+resolveDefines(className);
- // constructor => do backward class name substitution if needed
- //if (funcName==className) funcName=resolveDefines(className);
- //if (funcDecl.left(7)=="inline ") funcDecl=funcDecl.right(funcDecl.length()-7);
-
Debug::print(Debug::FindMembers,0,
"findMember() Parse results:\n"
" namespaceName=`%s'\n"
@@ -2693,7 +2717,9 @@ void findMember(Entry *root,QCString funcDecl,QCString related,bool overloaded,
argList /* dest argument list */
);
if (substDone) // delete old argument list
+ {
delete oldArgList;
+ }
substDone=TRUE;
}
@@ -2731,13 +2757,15 @@ void findMember(Entry *root,QCString funcDecl,QCString related,bool overloaded,
md->setArgumentList(argList);
}
else // no match -> delete argument list
+ {
delete argList;
+ }
}
if (matching)
{
//printf("addMemberDocs root->inLine=%d md->isInline()=%d\n",
// root->inLine,md->isInline());
- addMemberDocs(root,md,funcDecl,overloaded,nl);
+ addMemberDocs(root,md,funcDecl,0,overloaded,nl);
count++;
}
}
@@ -2865,7 +2893,7 @@ void findMember(Entry *root,QCString funcDecl,QCString related,bool overloaded,
if (!newMember && rmd) // member already exists as rmd -> add docs
{
//printf("addMemberDocs for related member %s\n",root->name.data());
- addMemberDocs(root,rmd,funcDecl,overloaded);
+ addMemberDocs(root,rmd,funcDecl,0,overloaded);
}
}
@@ -4817,8 +4845,17 @@ int main(int argc,char **argv)
}
else
{
- config=fileToString(argv[optind]);
- configName=argv[optind];
+ QFileInfo fi(argv[optind]);
+ if (fi.exists())
+ {
+ config=fileToString(argv[optind]);
+ configName=argv[optind];
+ }
+ else
+ {
+ err("Error: configuration file %s not found!\n",argv[optind]);
+ usage(argv[0]);
+ }
}
parseConfig(config);
diff --git a/src/htmlgen.cpp b/src/htmlgen.cpp
index b71f7a0..0b58044 100644
--- a/src/htmlgen.cpp
+++ b/src/htmlgen.cpp
@@ -207,9 +207,13 @@ void HtmlGenerator::writeStyleInfo(int part)
t << "TD.md { background-color: #f2f2ff }" << endl;
t << "DIV.groupHeader { margin-left: 16; margin-top: 12; margin-bottom: 6; font-weight: bold }" << endl;
t << "DIV.groupText { margin-left: 16; font-style: italic; font-size: smaller }" << endl;
- t << "FONT.keyword { color: #008000 }" << endl;
- t << "FONT.comment { color: #800000 }" << endl;
- t << "FONT.preprocessor { color: #806020 }" << endl;
+ t << "FONT.keyword { color: #008000 }" << endl;
+ t << "FONT.keywordtype { color: #604020 }" << endl;
+ t << "FONT.keywordflow { color: #e08000 }" << endl;
+ t << "FONT.comment { color: #800000 }" << endl;
+ t << "FONT.preprocessor { color: #806020 }" << endl;
+ t << "FONT.stringliteral { color: #002080 }" << endl;
+ t << "FONT.charliteral { color: #008080 }" << endl;
//t << "TD.groupLine { background-color: #3080ff }" << endl;
t << endl;
endPlainFile();
@@ -603,24 +607,6 @@ void HtmlGenerator::endMemberItem(bool)
t << endl;
}
-void HtmlGenerator::startParameter(bool first)
-{
- if (first)
- {
- t << endl << "</b></td>" << endl;
- t << "<td valign=bottom><b>" << endl;
- }
- else
- {
- t << "<tr><td></td><td><b>" << endl;
- }
-}
-
-void HtmlGenerator::endParameter(bool)
-{
- t << "</b></td></tr>" << endl;
-}
-
void HtmlGenerator::insertMemberAlign()
{
@@ -764,20 +750,81 @@ void HtmlGenerator::writeImage(const char *name,const char *,const char *)
void HtmlGenerator::startMemberDoc(const char *,const char *,const char *,const char *)
{
+ DBG_HTML(t << "<!-- startMemberDoc -->" << endl;)
t << "<p>" << endl;
t << "<table width=100% cellpadding=2 cellspacing=0 border=0>" << endl;
t << " <tr>" << endl;
t << " <td class=\"md\"><b>" << endl;
t << " <table cellspadding=0 cellspacing=0 border=0>" << endl;
+}
+
+void HtmlGenerator::startMemberDocPrefixItem()
+{
+ DBG_HTML(t << "<!-- startMemberDocPrefixItem -->" << endl;)
t << " <tr>" << endl;
- t << " <td valign=top><b>" << endl;
+ t << " <td colspan=\"2\"><b>" << endl;
+}
+
+void HtmlGenerator::endMemberDocPrefixItem()
+{
+ DBG_HTML(t << "<!-- endMemberDocPrefixItem -->" << endl;)
+ t << " </b></td>" << endl;
+ t << " </tr>" << endl;
+}
+
+void HtmlGenerator::startMemberDocName()
+{
+ DBG_HTML(t << "<!-- startMemberDocName -->" << endl;)
+ t << " <tr>" << endl;
+ t << " <td nowrap valign=\"top\"><b> " << endl;
+}
+
+void HtmlGenerator::endMemberDocName()
+{
+ DBG_HTML(t << "<!-- endMemberDocName -->" << endl;)
+ t << endl;
+ t << " </b></td>" << endl;
+}
+
+void HtmlGenerator::startParameter(bool first)
+{
+ if (first)
+ {
+ DBG_HTML(t << "<!-- startFirstParameter -->" << endl;)
+ t << " <td valign=\"bottom\"><b>" << endl;
+ }
+ else
+ {
+ DBG_HTML(t << "<!-- startParameter -->" << endl;)
+ t << " <tr>" << endl;
+ t << " <td></td>" << endl;
+ t << " <td><b>" << endl;
+ }
+}
+
+void HtmlGenerator::endParameter(bool first)
+{
+ if (first)
+ {
+ DBG_HTML(t << "<!-- endFirstParameter -->" << endl;)
+ t << endl;
+ t << " </b></td>" << endl;
+ //t << " <td width=\"300\"><img src=\"null.gif\"></td>" << endl;
+ t << " </tr>" << endl;
+ }
+ else
+ {
+ DBG_HTML(t << "<!-- endParameter -->" << endl;)
+ t << endl;
+ t << " </b></td>" << endl;
+ t << " </tr>" << endl;
+ }
}
void HtmlGenerator::endMemberDoc()
{
+ DBG_HTML(t << "<!-- endMemberDoc -->" << endl;)
t << endl;
- t << " </b></td>" << endl;
- t << " </tr>" << endl;
t << " </table>" << endl;
t << " </td>" << endl;
t << " </tr>" << endl;
diff --git a/src/htmlgen.h b/src/htmlgen.h
index 3fdc67c..7dc63e0 100644
--- a/src/htmlgen.h
+++ b/src/htmlgen.h
@@ -224,6 +224,10 @@ class HtmlGenerator : public OutputGenerator
void endTextBlock() {}
void lastIndexPage() {}
+ void startMemberDocPrefixItem();
+ void endMemberDocPrefixItem();
+ void startMemberDocName();
+ void endMemberDocName();
void startParameter(bool first);
void endParameter(bool last);
diff --git a/src/latexgen.h b/src/latexgen.h
index 8945723..a3e10c3 100644
--- a/src/latexgen.h
+++ b/src/latexgen.h
@@ -219,6 +219,11 @@ class LatexGenerator : public OutputGenerator
void startTextBlock(bool) {}
void endTextBlock() {}
+
+ void startMemberDocPrefixItem() {}
+ void endMemberDocPrefixItem() {}
+ void startMemberDocName() {}
+ void endMemberDocName() {}
void startParameter(bool) {}
void endParameter(bool) {}
diff --git a/src/mangen.h b/src/mangen.h
index c68ec5c..cb3b0a4 100644
--- a/src/mangen.h
+++ b/src/mangen.h
@@ -206,6 +206,11 @@ class ManGenerator : public OutputGenerator
void startTextBlock(bool) {}
void endTextBlock() {}
void lastIndexPage() {}
+
+ void startMemberDocPrefixItem() {}
+ void endMemberDocPrefixItem() {}
+ void startMemberDocName() {}
+ void endMemberDocName() {}
void startParameter(bool) {}
void endParameter(bool) {}
diff --git a/src/memberdef.cpp b/src/memberdef.cpp
index 1980587..dab56ea 100644
--- a/src/memberdef.cpp
+++ b/src/memberdef.cpp
@@ -73,6 +73,7 @@ static void writeDefArgumentList(OutputList &ol,ClassDef *cd,
if (argList==0) return; // member has no function like argument list
if (!md->isDefine()) ol.docify(" ");
ol.docify("("); // start argument list
+ ol.endMemberDocName();
Argument *a=argList->first();
QCString cName;
if (md->scopeDefTemplateArguments())
@@ -101,11 +102,11 @@ static void writeDefArgumentList(OutputList &ol,ClassDef *cd,
}
//printf("~~~ %s cName=%s\n",md->name().data(),cName.data());
+ //if (!md->isDefine()) ol.startParameter(TRUE); else ol.docify(" ");
+ ol.startParameter(TRUE);
bool first=TRUE;
while (a)
{
- if (!md->isDefine()) ol.startParameter(first); else ol.docify(" ");
- first=FALSE;
QRegExp re(")(");
int vp;
if (!a->attrib.isEmpty()) // argument has an IDL attribute
@@ -155,12 +156,17 @@ static void writeDefArgumentList(OutputList &ol,ClassDef *cd,
if (a)
{
ol.docify(", "); // there are more arguments
- if (!md->isDefine()) ol.endParameter(FALSE);
+ if (!md->isDefine())
+ {
+ ol.endParameter(first);
+ ol.startParameter(FALSE);
+ }
}
+ first=FALSE;
}
ol.pushGeneratorState();
ol.disableAllBut(OutputGenerator::Html);
- ol.writeString("&nbsp;");
+ if (!first) ol.writeString("&nbsp;");
ol.popGeneratorState();
ol.docify(")"); // end argument list
if (argList->constSpecifier)
@@ -192,11 +198,11 @@ static void writeTemplatePrefix(OutputList &ol,ArgumentList *al,bool br=TRUE)
ol.docify("> ");
if (br)
{
- ol.pushGeneratorState();
- ol.disable(OutputGenerator::Man);
- ol.disable(OutputGenerator::Latex);
- ol.lineBreak();
- ol.popGeneratorState();
+ // ol.pushGeneratorState();
+ // ol.disable(OutputGenerator::Man);
+ // ol.disable(OutputGenerator::Latex);
+ // ol.lineBreak();
+ // ol.popGeneratorState();
}
}
@@ -914,13 +920,17 @@ void MemberDef::writeDocumentation(MemberList *ml,OutputList &ol,
// )
if (scopeAl && !related) // class template prefix
{
+ ol.startMemberDocPrefixItem();
writeTemplatePrefix(ol,scopeAl);
+ ol.endMemberDocPrefixItem();
}
if (scopeAl && membAl) ol.docify(" ");
if (membAl) // function template prefix
{
+ ol.startMemberDocPrefixItem();
writeTemplatePrefix(ol,membAl);
+ ol.endMemberDocPrefixItem();
}
if (cd)
{
@@ -940,6 +950,7 @@ void MemberDef::writeDocumentation(MemberList *ml,OutputList &ol,
def=addTemplateNames(def,cName,tempArgListToString(scopeAl));
}
}
+ ol.startMemberDocName();
linkifyText(ol,scopeName,name(),def);
writeDefArgumentList(ol,cd,scopeName,this);
if (!init.isEmpty() && initLines==0) // add initializer
diff --git a/src/outputgen.h b/src/outputgen.h
index add49b5..d7d30a1 100644
--- a/src/outputgen.h
+++ b/src/outputgen.h
@@ -210,6 +210,10 @@ class OutputGenerator
virtual void endTextBlock() = 0;
virtual void lastIndexPage() = 0;
+ virtual void startMemberDocPrefixItem() = 0;
+ virtual void endMemberDocPrefixItem() = 0;
+ virtual void startMemberDocName() = 0;
+ virtual void endMemberDocName() = 0;
virtual void startParameter(bool) = 0;
virtual void endParameter(bool) = 0;
diff --git a/src/outputlist.h b/src/outputlist.h
index 7ae0827..d59320c 100644
--- a/src/outputlist.h
+++ b/src/outputlist.h
@@ -364,6 +364,14 @@ class OutputList
void lastIndexPage()
{ forall(&OutputGenerator::lastIndexPage); }
+ void startMemberDocPrefixItem()
+ { forall(&OutputGenerator::startMemberDocPrefixItem); }
+ void endMemberDocPrefixItem()
+ { forall(&OutputGenerator::endMemberDocPrefixItem); }
+ void startMemberDocName()
+ { forall(&OutputGenerator::startMemberDocName); }
+ void endMemberDocName()
+ { forall(&OutputGenerator::endMemberDocName); }
void startParameter(bool first)
{ forall(&OutputGenerator::startParameter,first); }
void endParameter(bool last)
diff --git a/src/rtfgen.h b/src/rtfgen.h
index f40c71e..634cfd3 100644
--- a/src/rtfgen.h
+++ b/src/rtfgen.h
@@ -208,6 +208,10 @@ class RTFGenerator : public OutputGenerator
void endTextBlock();
void lastIndexPage();
+ void startMemberDocPrefixItem() {}
+ void endMemberDocPrefixItem() {}
+ void startMemberDocName() {}
+ void endMemberDocName() {}
void startParameter(bool) {}
void endParameter(bool) {}
diff --git a/src/scanner.l b/src/scanner.l
index 24047ea..6f2fea7 100644
--- a/src/scanner.l
+++ b/src/scanner.l
@@ -151,6 +151,7 @@ static QCString formulaText;
static QCString sectionRef;
static bool insideIDL = FALSE;
static bool insideCppQuote = FALSE;
+static bool insideVerbatim = FALSE;
static int depthIf;
// state variable for reading the argument list of a function
@@ -778,7 +779,7 @@ static QCString findAndCopyImage(const char *fileName,ImageTypes type)
FileDef *fd;
if ((fd=findFileDef(&imageNameDict,fileName,ambig)))
{
- QFile inImage(fd->absFilePath());
+ QFile inImage(fd->absFilePath().data());
if (inImage.open(IO_ReadOnly))
{
result = fileName;
@@ -798,7 +799,7 @@ static QCString findAndCopyImage(const char *fileName,ImageTypes type)
break;
}
QCString outputFile = outputDir+"/"+result;
- QFile outImage(outputFile);
+ QFile outImage(outputFile.data());
if (outImage.open(IO_WriteOnly)) // copy the image
{
char *buffer = new char[inImage.size()];
@@ -1125,7 +1126,7 @@ DOCPARAM ([a-z_A-Z0-9:\.\-]+)|("\"".*"\"")
<DocScan>^{B}*(("//"{B}*)?)"*"*{B}*"-"{B}+ { /* found list item marker */
addListItemMarker(yytext);
}
-<DocScan>\n{B}*"-" {
+<DocScan>\n{B}*(("//"{B}*)?)"*"*{B}*"-"{B}+ {
addListItemMarker(yytext+1);
}
<DocScan>"<!--" { BEGIN(DocSkipHtmlComment); }
@@ -1188,10 +1189,12 @@ DOCPARAM ([a-z_A-Z0-9:\.\-]+)|("\"".*"\"")
}
<DocScan>{CMD}"verbatim"/[^a-z_A-Z0-9] {
outDoc->startCodeFragment();
+ insideVerbatim=TRUE;
BEGIN(DocVerbatim);
}
<DocVerbatim>{CMD}"endverbatim"/[^a-z_A-Z0-9] {
outDoc->endCodeFragment();
+ insideVerbatim=FALSE;
BEGIN(DocScan);
}
<DocVerbatim>[^\n\\\@]*"\n" {
@@ -1939,14 +1942,30 @@ DOCPARAM ([a-z_A-Z0-9:\.\-]+)|("\"".*"\"")
<DocScan>"<"{OL}{ATTR}">" { outDoc->startEnumList();
currentListIndentLevel++;
}
-<DocScan>"</"{OL}{ATTR}">" { outDoc->endEnumList();
- currentListIndentLevel--;
+<DocScan>"</"{OL}{ATTR}">" {
+ if (currentListIndentLevel<=0)
+ {
+ warn("Warning: more </ol> tags than <ol> tags in the documentation of %s\n",yyFileName);
+ }
+ else
+ {
+ outDoc->endEnumList();
+ currentListIndentLevel--;
+ }
}
<DocScan>"<"{UL}{ATTR}">" { outDoc->startItemList();
currentListIndentLevel++;
}
-<DocScan>"</"{UL}{ATTR}">" { outDoc->endItemList();
- currentListIndentLevel--;
+<DocScan>"</"{UL}{ATTR}">" {
+ if (currentListIndentLevel<=0)
+ {
+ warn("Warning: more </ul> tags than <ul> tags in the documentation of %s\n",yyFileName);
+ }
+ else
+ {
+ outDoc->endItemList();
+ currentListIndentLevel--;
+ }
}
<DocScan>"<"{LI}{ATTR}">" { outDoc->writeListItem(); }
<DocScan>"</"{LI}{ATTR}">"
@@ -1958,8 +1977,16 @@ DOCPARAM ([a-z_A-Z0-9:\.\-]+)|("\"".*"\"")
<DocScan>"<"{DL}{ATTR}">" { outDoc->startDescription();
currentListIndentLevel++;
}
-<DocScan>"</"{DL}{ATTR}">" { outDoc->endDescription();
- currentListIndentLevel--;
+<DocScan>"</"{DL}{ATTR}">" {
+ if (currentListIndentLevel<=0)
+ {
+ warn("Warning: more </dl> tags than <dl> tags in the documentation of %s\n",yyFileName);
+ }
+ else
+ {
+ outDoc->endDescription();
+ currentListIndentLevel--;
+ }
}
<DocScan>"<"{DT}{ATTR}">" { outDoc->startDescItem(); }
<DocScan>"</"{DT}{ATTR}">"
@@ -2813,7 +2840,7 @@ DOCPARAM ([a-z_A-Z0-9:\.\-]+)|("\"".*"\"")
<CopyCurly>"'"\\[0-7]{1,3}"'" { *pCopyCurlyString+=yytext; }
<CopyCurly>"'"\\."'" { *pCopyCurlyString+=yytext; }
<CopyCurly>"'"."'" { *pCopyCurlyString+=yytext; }
-<CopyCurly>[^"'{}\n]+ {
+<CopyCurly>[^"'{}\/\n]+ {
*pCopyCurlyString+=yytext;
}
<CopyCurly>\n {
@@ -3316,6 +3343,7 @@ DOCPARAM ([a-z_A-Z0-9:\.\-]+)|("\"".*"\"")
BEGIN( ReadFuncArgType );
}
<CopyArgCommentLine>\n { fullArgString+=yytext;
+ yyLineNr++;
if (lastCopyArgChar!=0)
unput(lastCopyArgChar);
BEGIN( ReadFuncArgType );
@@ -4870,11 +4898,12 @@ void parseDocument(OutputList &ol,const QCString &docString)
scanYYrestart( scanYYin );
BEGIN( DocScan );
insideArgumentList = FALSE;
+ insideVerbatim = FALSE;
scanYYlex();
if (insideArgumentList) { insideArgumentList=FALSE; outDoc->endItemList(); }
if (insideItemList) { forceEndItemList(); }
if (inBlock()) endBlock();
- if (currentListIndentLevel!=0)
+ if (currentListIndentLevel>0)
{
if (!refName.isEmpty())
{
@@ -4902,6 +4931,10 @@ void parseDocument(OutputList &ol,const QCString &docString)
{
forceEndTable();
}
+ if (insideVerbatim)
+ {
+ warn("Warning: file ended inside a \\verbatim block!\n");
+ }
ol+=*outDoc;
delete outDoc; outDoc=0;
return;
@@ -4931,6 +4964,7 @@ void parseDoc(OutputList &ol,const char *clName,
refName="<unknown>";
}
parseDocument(ol,docString);
+
}
//----------------------------------------------------------------------------
diff --git a/src/util.cpp b/src/util.cpp
index 0af45f5..f20f8ab 100644
--- a/src/util.cpp
+++ b/src/util.cpp
@@ -455,7 +455,14 @@ QCString argListToString(ArgumentList *al)
result+="(";
while (a)
{
- result+= a->type+" "+a->name+a->array;
+ if (!a->name.isEmpty() || !a->array.isEmpty())
+ {
+ result+= a->type+" "+a->name+a->array;
+ }
+ else
+ {
+ result+= a->type;
+ }
a = al->next();
if (a) result+=",";
}
@@ -877,7 +884,7 @@ static QCString trimScope(const QCString &name,const QCString &s)
return result;
}
-static QCString trimBaseClassScope(BaseClassList *bcl,const QCString &s,int level=0)
+void trimBaseClassScope(BaseClassList *bcl,QCString &s,int level=0)
{
//printf("trimBaseClassScope level=%d `%s'\n",level,s.data());
BaseClassListIterator bcli(*bcl);
@@ -885,18 +892,18 @@ static QCString trimBaseClassScope(BaseClassList *bcl,const QCString &s,int leve
for (;(bcd=bcli.current());++bcli)
{
ClassDef *cd=bcd->classDef;
+ //printf("Trying class %s\n",cd->name().data());
int spos=s.find(cd->name()+"::");
if (spos!=-1)
{
- return s.left(spos)+s.right(
- s.length()-spos-cd->name().length()-2
+ s = s.left(spos)+s.right(
+ s.length()-spos-cd->name().length()-2
);
}
//printf("base class `%s'\n",cd->name().data());
if (cd->baseClasses()->count()>0)
trimBaseClassScope(cd->baseClasses(),s,level+1);
}
- return s;
}
/*! if either t1 or t2 contains a namespace scope, then remove that
@@ -938,6 +945,44 @@ static void trimNamespaceScope(QCString &t1,QCString &t2)
}
}
+/*! According to the C++ spec and Ivan Vecerina:
+
+ Parameter declarations that differ only in the presence or absence
+ of const and/or volatile are equivalent.
+
+ So the following example, show what is stripped by this routine
+ for const. The same is done for volatile.
+
+ \code
+ const T param -> T param // not relevant
+ const T& param -> const T& param // const needed
+ T* const param -> T* param // not relevant
+ const T* param -> const T* param // const needed
+ \endcode
+ */
+void stripIrrelevantConstVolatile(QCString &s)
+{
+ int i,j;
+ i = s.find("const ");
+ if (i!=-1)
+ {
+ // no & or * after the const
+ if ((j=s.find('*',i+6))==-1 && (j=s.find('&',i+6))==-1)
+ {
+ s=s.left(i)+s.right(s.length()-i-6);
+ }
+ }
+ i = s.find("volatile ");
+ if (i!=-1)
+ {
+ // no & or * after the volatile
+ if ((j=s.find('*',i+9))==-1 && (j=s.find('&',i+9))==-1)
+ {
+ s=s.left(i)+s.right(s.length()-i-9);
+ }
+ }
+}
+
//----------------------------------------------------------------------
// Matches the arguments list srcAl with the argument list dstAl
// Returns TRUE if the argument lists are equal. Two argument list are
@@ -1014,6 +1059,8 @@ bool matchArguments(ArgumentList *srcAl,ArgumentList *dstAl,
QCString dstAType=trimTemplateSpecifiers(className,dstA->type);
if (srcAType.left(6)=="class ") srcAType=srcAType.right(srcAType.length()-6);
if (dstAType.left(6)=="class ") dstAType=dstAType.right(dstAType.length()-6);
+ stripIrrelevantConstVolatile(srcAType);
+ stripIrrelevantConstVolatile(dstAType);
if (srcAType!=dstAType) // check if the argument only differs on name
{
@@ -1039,8 +1086,8 @@ bool matchArguments(ArgumentList *srcAl,ArgumentList *dstAl,
cd=getClass(className);
if (cd && cd->baseClasses()->count()>0)
{
- srcAType=trimBaseClassScope(cd->baseClasses(),srcAType);
- dstAType=trimBaseClassScope(cd->baseClasses(),dstAType);
+ trimBaseClassScope(cd->baseClasses(),srcAType);
+ trimBaseClassScope(cd->baseClasses(),dstAType);
}
//printf("trimBaseClassScope: `%s' <=> `%s'\n",srcAType.data(),dstAType.data());
}