summaryrefslogtreecommitdiffstats
path: root/src/doxygen.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/doxygen.cpp')
-rw-r--r--src/doxygen.cpp929
1 files changed, 562 insertions, 367 deletions
diff --git a/src/doxygen.cpp b/src/doxygen.cpp
index 8c11c0b..76518ba 100644
--- a/src/doxygen.cpp
+++ b/src/doxygen.cpp
@@ -15,7 +15,7 @@
*
*/
-#include <qstring.h>
+#include "qtbc.h"
#include <qfileinf.h>
#include <qfile.h>
#include <qdir.h>
@@ -109,6 +109,7 @@ QTextStream tagFile;
void addMemberDocs(Entry *root,MemberDef *md, const char *funcDecl,
bool over_load);
+const char idMask[] = "[A-Za-z_][A-Za-z_0-9]*";
//----------------------------------------------------------------------
// Returns the standard string that is generated when the \overload
@@ -166,8 +167,8 @@ void buildGroupList(Entry *root)
//
// if ((gd=groupDict[root->name]))
// {
-// QListIterator<QString> sli(*root->groups);
-// QString *s;
+// QListIterator<QCString> sli(*root->groups);
+// QCString *s;
// for (;(s=sli.current());++sli)
// {
// GroupDef *pgd;
@@ -192,7 +193,7 @@ void buildGroupList(Entry *root)
void buildFileList(Entry *root)
{
if (((root->section==Entry::FILEDOC_SEC) ||
- ((root->section & Entry::FILE_MASK) && extractAllFlag)) &&
+ ((root->section & Entry::FILE_MASK) && Config::extractAllFlag)) &&
root->name.length()>0
)
{
@@ -212,8 +213,8 @@ void buildFileList(Entry *root)
fd->setDocumentation(root->doc);
fd->setBriefDescription(root->brief);
fd->addSectionsToDefinition(root->anchors);
- QListIterator<QString> sli(*root->groups);
- QString *s;
+ QListIterator<QCString> sli(*root->groups);
+ QCString *s;
for (;(s=sli.current());++sli)
{
GroupDef *gd=0;
@@ -307,11 +308,11 @@ void addIncludeFile(ClassDef *cd,FileDef *ifd,Entry *root)
/*! Input is a scopeName, output is the scopename split into a
* namespace part (as large as possible) and a classname part.
*/
-void extractNamespaceName(const QString &scopeName,
- QString &className,QString &namespaceName)
+void extractNamespaceName(const QCString &scopeName,
+ QCString &className,QCString &namespaceName)
{
- QString clName=scopeName.copy();
- QString nsName;
+ QCString clName=scopeName.copy();
+ QCString nsName;
if (clName.length()>0 && namespaceDict[clName])
{ // the whole name is a namespace
namespaceName=clName.copy();
@@ -346,7 +347,9 @@ static bool addNamespace(Entry *root,ClassDef *cd)
if (e->section==Entry::NAMESPACE_SEC)
{
NamespaceDef *nd=0;
- if (!e->name.isEmpty() && (nd=namespaceDict[e->name]))
+ if (!e->name.isEmpty() && e->name.at(0)!='@' &&
+ (nd=namespaceDict[e->name])
+ )
{
cd->setNamespace(nd);
nd->insertClass(cd);
@@ -359,6 +362,7 @@ static bool addNamespace(Entry *root,ClassDef *cd)
return FALSE;
}
+
//----------------------------------------------------------------------
// build a list of all classes mentioned in the documentation
// and all classes that have a documentation block before their definition.
@@ -370,7 +374,7 @@ void buildClassList(Entry *root)
root->name.length()>0
)
{
- QString fullName=root->name.copy();
+ QCString fullName=root->name.copy();
if (fullName.length()==0)
{
// this should not be called
@@ -379,19 +383,7 @@ void buildClassList(Entry *root)
}
else
{
- //QString className;
- //QString namespaceName;
- //extractNamespaceName(fullName,className,namespaceName);
-
- //printf("Found class %s in %s at line %d\n",fullName.data(),
- // root->fileName.data(),root->startLine);
- // add class name substitution entry iff the class name is alterned by a
- // define. This is needed to properly document Qt's template classes
- // (although, it's quite general)
- //if (resolveDefines(fullName)!=fullName)
- //{
- // substituteDict.insert(resolveDefines(fullName),new QString(fullName));
- //}
+ fullName=stripAnnonymousScope(fullName);
bool ambig;
ClassDef *cd;
@@ -427,13 +419,7 @@ void buildClassList(Entry *root)
}
addNamespace(root,cd);
}
- else if (fullName[0]!='@' /* &&
- (root->doc.length()>0 ||
- root->brief.length()>0 ||
- extractAllFlag
- )*/
- )
- // new class
+ else // new class
{
ClassDef::CompoundType sec=ClassDef::Class;
switch(root->section)
@@ -448,13 +434,12 @@ void buildClassList(Entry *root)
ClassDef *cd=new ClassDef(fullName,sec);
cd->setDocumentation(root->doc); // copy docs to definition
cd->setBriefDescription(root->brief);
- //printf("new ClassDef tempArgList=%p\n",root->tArgList);
cd->setTemplateArguments(root->tArgList);
cd->setProtection(root->protection);
cd->addSectionsToDefinition(root->anchors);
- QListIterator<QString> sli(*root->groups);
- QString *s;
+ QListIterator<QCString> sli(*root->groups);
+ QCString *s;
for (;(s=sli.current());++sli)
{
GroupDef *gd=0;
@@ -475,7 +460,7 @@ void buildClassList(Entry *root)
// if the class is not in a namespace then we insert
// it in the file definition
if (!found && ifd) ifd->insertClass(cd);
-
+
// the empty string test is needed for extract all case
cd->setBriefDescription(root->brief);
cd->insertUsedFile(root->fileName);
@@ -506,7 +491,7 @@ void buildNamespaceList(Entry *root)
root->name.length()>0
)
{
- QString fullName=root->name.copy();
+ QCString fullName=root->name.copy();
if (fullName.length()==0)
{
// this should not be called
@@ -549,7 +534,7 @@ void buildNamespaceList(Entry *root)
}
else /* if (root->doc.length()>0 ||
root->brief.length()>0 ||
- extractAllFlag
+ Config::extractAllFlag
)
*/
{
@@ -558,8 +543,8 @@ void buildNamespaceList(Entry *root)
nd->setBriefDescription(root->brief);
nd->addSectionsToDefinition(root->anchors);
- QListIterator<QString> sli(*root->groups);
- QString *s;
+ QListIterator<QCString> sli(*root->groups);
+ QCString *s;
for (;(s=sli.current());++sli)
{
GroupDef *gd=0;
@@ -645,35 +630,29 @@ void buildVarList(Entry *root)
}
}
- QString scope,name=root->name.copy();
+ QCString scope,name=root->name.copy();
bool stat=root->stat;
- ClassDef *cd=0;
Entry *p = root->parent;
- while ((p->section & Entry::COMPOUND_MASK) ||
- p->section==Entry::NAMESPACE_SEC)
+ while ((p->section & Entry::SCOPE_MASK))
{
- if (p->name.length()>0 && p->name[0]!='@')
+ QCString scopeName = stripAnnonymousScope(p->name);
+ if (!scopeName.isEmpty())
{
- if (!scope.isEmpty()) scope.prepend("::");
- scope.prepend(p->name);
+ scope.prepend(scopeName);
break;
}
+ //if (p->name.length()>0 && p->name[0]!='@')
+ //{
+ // if (!scope.isEmpty()) scope.prepend("::");
+ // scope.prepend(p->name);
+ // break;
+ //}
p=p->parent;
}
//printf("scope=%s\n",scope.data());
int ni;
-#if 0
- if ((ni=root->name.findRev("::"))!=-1)
- {
- if (scope.length()>0) scope+="::";
- scope+=root->name.left(ni);
- name=root->name.right(root->name.length()-ni-2);
- stat=TRUE;
- }
-#endif
-
if ((ni=root->name.findRev("::"))!=-1) goto nextMember;
/* skip this member, because it is a
* static variable definition (always?), which will be
@@ -684,7 +663,7 @@ void buildVarList(Entry *root)
MemberDef::MemberType mtype;
// NamespaceDef *nd = 0;
- QString type=root->type.stripWhiteSpace();
+ QCString type=root->type.stripWhiteSpace();
if (type=="@")
mtype=MemberDef::EnumValue;
else if (type.left(8)=="typedef ")
@@ -694,6 +673,7 @@ void buildVarList(Entry *root)
else
mtype=MemberDef::Variable;
+ ClassDef *cd=0;
if (scope.length()>0 && name.length()>0 && (cd=getClass(scope)))
{
@@ -712,7 +692,7 @@ void buildVarList(Entry *root)
// scope+=cd->getTemplateNameString();
//}
// generate member definition.
- QString def;
+ QCString def;
if (root->type.length()>0)
{
if (mtype==MemberDef::Friend)
@@ -743,23 +723,6 @@ void buildVarList(Entry *root)
if (md->memberClass()==cd) // member already in the scope
{
addMemberDocs(root,md,def,FALSE);
-
-#if 0
- // always trust the most protected scope, so adjust if needed
- // This is needed to properly place static private variables,
- // which are defined in a `public' scope.
- printf("Checking protection level\n");
- if (root->protection==Private || md->protection()!=Private)
- {
- printf("Set to private\n");
- md->setProtection(Private);
- }
- else if (root->protection==Protected && md->protection()==Public)
- {
- printf("Set to protected\n");
- md->setProtection(Protected);
- }
-#endif
found=TRUE;
}
md=mn->next();
@@ -802,56 +765,6 @@ void buildVarList(Entry *root)
cd->insertUsedFile(root->fileName);
}
}
-#if 0
- else if (scope.length()>0 && name.length()>0 && (nd=namespaceDict[scope]))
- {
- Debug::print(Debug::Variables,0,
- " namespace variable:\n"
- " type=`%s' scope=`%s' name=`%s' args=`%s' prot=`%d\n",
- root->type.data(),
- scope.data(),
- name.data(),
- root->args.data(),
- root->protection
- );
- // new global variable, enum value or typedef
- MemberDef *md=new MemberDef(root->type,name,root->args,0,
- Public, Normal,root->stat,FALSE,
- mtype,0,0);
- md->setDefFile(root->fileName);
- md->setDefLine(root->startLine);
- md->setDocumentation(root->doc);
- md->setBriefDescription(root->brief);
- md->addSectionsToDefinition(root->anchors);
- QString def;
- nd->insertMember(md);
- md->setNamespace(nd);
- if (root->type.length()>0)
- {
- def=root->type+" "+nd->name()+"::"+name+root->args;
- }
- else
- {
- def=nd->name()+"::"+name+root->args;
- }
- if (def.left(7)=="static ") def=def.right(def.length()-7);
- md->setDefinition(def);
-
- MemberName *mn;
- // add member definition to the list of globals
- if ((mn=namespaceNameDict[name]))
- {
- mn->inSort(md);
- }
- else
- {
- mn = new MemberName(name);
- mn->inSort(md);
- namespaceNameDict.insert(name,mn);
- namespaceNameList.inSort(mn);
- }
- }
-#endif
else if (name.length()>0) // global variable
{
Debug::print(Debug::Variables,0,
@@ -873,15 +786,15 @@ void buildVarList(Entry *root)
md->setDocumentation(root->doc);
md->setBriefDescription(root->brief);
md->addSectionsToDefinition(root->anchors);
- QString def;
+ QCString def;
// see if the function is inside a namespace
NamespaceDef *nd = 0;
- if (root->parent->section == Entry::NAMESPACE_SEC )
+ if (scope.length()>0)
{
- nd = namespaceDict[root->parent->name];
+ nd = namespaceDict[scope];
}
- if (nd)
+ if (nd && !nd->name().isEmpty() && nd->name().at(0)!='@')
{
nd->insertMember(md);
md->setNamespace(nd);
@@ -901,8 +814,8 @@ void buildVarList(Entry *root)
}
// determine the definition of the global variable
- if (nd) // variable is inside a namespace, so put the scope
- // before the name
+ if (nd && !nd->name().isEmpty() && nd->name().at(0)!='@')
+ // variable is inside a namespace, so put the scope before the name
{
if (root->type.length()>0)
{
@@ -961,20 +874,20 @@ void buildMemberList(Entry *root)
{
Debug::print(Debug::Functions,0,
"FUNCTION_SEC:\n"
- " `%s' `%s'::`%s' `%s' relates=`%s' file=`%s' #targs=%d\n",
+ " `%s' `%s'::`%s' `%s' relates=`%s' file=`%s' #targs=%d docs=`%s'\n",
root->type.data(),
root->parent->name.data(),
root->name.data(),
root->args.data(),
root->relates.data(),
root->fileName.data(),
- root->tArgList ? (int)root->tArgList->count() : -1
+ root->tArgList ? (int)root->tArgList->count() : -1,
+ root->doc.data()
);
bool isFriend=root->type.find("friend ")!=-1;
- //if (isFriend && root->relates.length()==0)
- // root->relates=root->parent->name.copy();
- if (root->name.length()>0 /* && !isFriend */)
+
+ if (root->name.length()>0)
{
ClassDef *cd=0;
@@ -983,11 +896,12 @@ void buildMemberList(Entry *root)
//printf("root->parent=`%s' cd=%p root->type.find(re,0)=%d\n",
// root->parent->name.data(),getClass(root->parent->name),
// root->type.find(re,0));
+ QCString scope=stripAnnonymousScope(root->parent->name.copy());
int i;
if (root->parent &&
root->parent->name.length()>0 &&
(root->parent->section & Entry::COMPOUND_MASK) &&
- (cd=getClass(root->parent->name)) &&
+ (cd=getClass(scope)) &&
// do some fuzzy things to exclude function pointers
(root->type.isNull() || root->type.find(re,0)==-1 ||
root->type.find(")(")!=-1 || root->type.find("operator")!=-1
@@ -1001,7 +915,7 @@ void buildMemberList(Entry *root)
root->type=root->type.left(i+l);
}
- QString name=removeRedundantWhiteSpace(root->name);
+ QCString name=removeRedundantWhiteSpace(root->name);
if (name.left(2)=="::") name=name.right(name.length()-2);
MemberDef::MemberType mtype;
@@ -1009,7 +923,16 @@ void buildMemberList(Entry *root)
else if (root->sig) mtype=MemberDef::Signal;
else if (root->slot) mtype=MemberDef::Slot;
else mtype=MemberDef::Function;
- // new member of function, signal or slot.
+
+ //if (Config::includeSourceFlag && !root->body.isEmpty())
+ //{
+ // printf("Function: %s\n-----------------\n%s\n------------------\n",
+ // root->name.data(),root->body.data());
+ //}
+
+ // new member function, signal or slot.
+ //printf("new member: %s class template args=`%s'\n",
+ // root->args.data(),argListToString(cd->templateArguments()).data());
MemberDef *md=new MemberDef(root->type,name,root->args,root->exception,
root->protection,root->virt,root->stat,root->relates.length()>0,
mtype,root->tArgList,root->argList);
@@ -1018,8 +941,10 @@ void buildMemberList(Entry *root)
md->setDefLine(root->startLine);
md->setDocumentation(root->doc);
md->setBriefDescription(root->brief);
+ md->setBody(root->body);
+ //md->setScopeTemplateArguments(cd->templateArguments());
md->addSectionsToDefinition(root->anchors);
- QString def;
+ QCString def;
if (root->relates.length()>0 || isFriend)
{
if (root->type.length()>0)
@@ -1047,7 +972,6 @@ void buildMemberList(Entry *root)
}
else
{
- QString scope=root->parent->name.copy();
if (root->type.length()>0)
{
if (root->argList)
@@ -1110,7 +1034,9 @@ void buildMemberList(Entry *root)
!(root->parent->section & Entry::COMPOUND_MASK) &&
root->name.find("::")==-1 &&
root->relates.length()==0 &&
- root->type.left(7)!="extern ")
+ root->type.left(7)!="extern " &&
+ root->type.left(8)!="typedef "
+ )
// no member => unrelated function
{
/* check the uniqueness of the function name in the file.
@@ -1153,7 +1079,7 @@ void buildMemberList(Entry *root)
// root->type.data(),root->name.data(),root->args.data());
// new global function
- QString name=removeRedundantWhiteSpace(root->name);
+ QCString name=removeRedundantWhiteSpace(root->name);
MemberDef *md=new MemberDef(root->type,name,root->args,root->exception,
root->protection,root->virt,root->stat,FALSE,
MemberDef::Function,root->tArgList,root->argList);
@@ -1162,8 +1088,9 @@ void buildMemberList(Entry *root)
md->setDocumentation(root->doc);
md->setBriefDescription(root->brief);
md->setPrototype(root->proto);
+ md->setBody(root->body);
md->addSectionsToDefinition(root->anchors);
- QString def;
+ QCString def;
if (root->type.length()>0)
{
if (root->argList)
@@ -1205,7 +1132,8 @@ void buildMemberList(Entry *root)
{
nd = namespaceDict[root->parent->name];
}
- if (nd)
+
+ if (nd && !nd->name().isEmpty() && nd->name().at(0)!='@')
{
nd->insertMember(md);
md->setNamespace(nd);
@@ -1386,22 +1314,23 @@ void computeClassRelations(Entry *root)
if (!cd->visited)
{
cd->visited=TRUE; // mark class as used (in case the are multiple classes
- // with the same name!)
+ // with the same name!)
if (root->extends->count()>0) // there are base classes
{
- QString scopePrefix;
+ QCString scopePrefix;
Entry *p=root->parent;
+ bool found=FALSE;
// For nested classes the base class could also be nested!
// To find the correct scope, we try to prepend the scope to the base
// name, starting with the largest, most inner scope.
- while (p->section&Entry::COMPOUND_MASK)
+ while (p->section&Entry::COMPOUND_MASK && !found)
{
scopePrefix=p->name+"::";
QList<BaseInfo> *baseList=root->extends;
BaseInfo *bi=baseList->first();
- while (bi) // for each base class
+ while (bi && !found) // for each base class
{
- QString cName=scopePrefix+bi->name;
+ QCString cName=scopePrefix+bi->name;
//printf("Base class %s\n",cName.data());
ClassDef *baseClass=getClass(cName);
if (baseClass) // base class is documented
@@ -1411,6 +1340,7 @@ void computeClassRelations(Entry *root)
cd->insertBaseClass(baseClass,bi->prot,bi->virt);
// add this class as super class to the base class
baseClass->insertSuperClass(cd,bi->prot,bi->virt);
+ found=TRUE;
}
//else // base class not documented
//{
@@ -1421,71 +1351,75 @@ void computeClassRelations(Entry *root)
}
p=p->parent;
}
- // The base class could ofcouse also be a non-nested class
- QList<BaseInfo> *baseList=root->extends;
- BaseInfo *bi=baseList->first();
- while (bi) // for each base class
+ if (!found)
{
- ClassDef *baseClass=getClass(bi->name);
- //printf("baseClass %s of %s found (%s and %s)\n",
- // bi->name.data(),
- // root->name.data(),
- // (bi->prot==Private)?"private":((bi->prot==Protected)?"protected":"public"),
- // (bi->virt==Normal)?"normal":"virtual"
- // );
- int i;
- QString templSpec,baseClassName=bi->name.copy();
- if (!baseClass && (i=bi->name.find('<'))!=-1)
- // base class has template specifiers
- {
- // TODO: here we should try to find the correct template specialization
- // but for now, we only look for the unspecializated base class.
- baseClassName=bi->name.left(i);
- baseClass=getClass(baseClassName);
- templSpec=bi->name.right(bi->name.length()-i);
- }
- if (baseClass) // base class is documented
- {
- // add base class to this class
- cd->insertBaseClass(baseClass,bi->prot,bi->virt,templSpec);
- // add this class as super class to the base class
- baseClass->insertSuperClass(cd,bi->prot,bi->virt,templSpec);
- }
- else // base class not documented
+ // The base class could ofcouse also be a non-nested class
+ QList<BaseInfo> *baseList=root->extends;
+ BaseInfo *bi=baseList->first();
+ while (bi) // for each base class
{
- NamespaceDef *nd=cd->getNamespace();
- //printf("Found undocumented base class `%s' namespace scope=`%s'\n",
- // bi->name.data(),nd ? nd->name().data() : "<none>");
- if (nd && (baseClass=getClass(nd->name()+"::"+baseClassName)))
- // class is defined inside namespace
+ ClassDef *baseClass=getClass(bi->name);
+ //printf("baseClass %s of %s found (%s and %s)\n",
+ // bi->name.data(),
+ // root->name.data(),
+ // (bi->prot==Private)?"private":((bi->prot==Protected)?"protected":"public"),
+ // (bi->virt==Normal)?"normal":"virtual"
+ // );
+ int i;
+ QCString templSpec,baseClassName=bi->name.copy();
+ if (!baseClass && (i=bi->name.find('<'))!=-1)
+ // base class has template specifiers
{
- // add base class to this class
- cd->insertBaseClass(baseClass,bi->prot,bi->virt,templSpec);
- // add this class as super class to the base class
- baseClass->insertSuperClass(cd,bi->prot,bi->virt,templSpec);
+ // TODO: here we should try to find the correct template specialization
+ // but for now, we only look for the unspecializated base class.
+ baseClassName=bi->name.left(i);
+ baseClass=getClass(baseClassName);
+ templSpec=bi->name.right(bi->name.length()-i);
}
- else // undocumented base class
+ if (baseClass) // base class is documented
{
- baseClass=new ClassDef(bi->name,ClassDef::Class);
// add base class to this class
cd->insertBaseClass(baseClass,bi->prot,bi->virt,templSpec);
// add this class as super class to the base class
baseClass->insertSuperClass(cd,bi->prot,bi->virt,templSpec);
- // the undocumented base was found in this file
- baseClass->insertUsedFile(root->fileName);
- // add class to the list
- classList.inSort(baseClass);
- //printf("ClassDict.insert(%s)\n",resolveDefines(fullName).data());
- //classDict.insert(resolveDefines(bi->name),baseClass);
- classDict.insert(bi->name,baseClass);
}
+ else // base class not documented
+ {
+ NamespaceDef *nd=cd->getNamespace();
+ //printf("Found undocumented base class `%s' namespace scope=`%s'\n",
+ // bi->name.data(),nd ? nd->name().data() : "<none>");
+ if (nd && (baseClass=getClass(nd->name()+"::"+baseClassName)))
+ // class is defined inside namespace
+ {
+ // add base class to this class
+ cd->insertBaseClass(baseClass,bi->prot,bi->virt,templSpec);
+ // add this class as super class to the base class
+ baseClass->insertSuperClass(cd,bi->prot,bi->virt,templSpec);
+ }
+ else // undocumented base class
+ {
+ //printf(">>> Undocumented base class = %s\n",bi->name.data());
+ baseClass=new ClassDef(baseClassName,ClassDef::Class);
+ // add base class to this class
+ cd->insertBaseClass(baseClass,bi->prot,bi->virt,templSpec);
+ // add this class as super class to the base class
+ baseClass->insertSuperClass(cd,bi->prot,bi->virt,templSpec);
+ // the undocumented base was found in this file
+ baseClass->insertUsedFile(root->fileName);
+ // add class to the list
+ classList.inSort(baseClass);
+ //printf("ClassDict.insert(%s)\n",resolveDefines(fullName).data());
+ //classDict.insert(resolveDefines(bi->name),baseClass);
+ classDict.insert(bi->name,baseClass);
+ }
+ }
+ bi=baseList->next();
}
- bi=baseList->next();
}
}
// else // class has no base classes
// {
-// QString resName=resolveDefines(root->name);
+// QCString resName=resolveDefines(root->name);
// int i;
// // Check if this class is a template instance of another class.
// // If this is the case, we act as if this class `inherits' from the
@@ -1570,7 +1504,7 @@ void addMemberDocs(Entry *root,MemberDef *md, const char *funcDecl,
{
//printf("addMemberDocs: `%s'::`%s' `%s' funcDecl=`%s'\n",
// root->parent->name.data(),md->name().data(),md->argsString(),funcDecl);
- QString fDecl=funcDecl;
+ QCString fDecl=funcDecl;
// strip extern specifier
if (fDecl.left(7)=="extern ") fDecl=fDecl.right(fDecl.length()-7);
md->setDefinition(fDecl);
@@ -1580,10 +1514,13 @@ void addMemberDocs(Entry *root,MemberDef *md, const char *funcDecl,
cd ? cd->name().data() : 0,
nd ? nd->name().data() : 0
)
- ) mergeArguments(md->argumentList(),root->argList);
+ )
+ {
+ mergeArguments(md->argumentList(),root->argList);
+ }
if (over_load) // the \overload keyword was used
{
- QString doc=getOverloadDocs();
+ QCString doc=getOverloadDocs();
if (!root->doc.isNull())
{
doc+="<p>";
@@ -1596,7 +1533,7 @@ void addMemberDocs(Entry *root,MemberDef *md, const char *funcDecl,
// documentation outside a compound overrides the documentation inside it
if ( /* !md->isStatic() && !root->stat && do not replace doc of a static */
(
- !md->documentation() || /* no docs yet */
+ md->documentation().isEmpty() || /* no docs yet */
(root->parent->name.isNull() && /* or overwrite prototype docs */
!root->proto && md->isPrototype() /* with member definition docs */
)
@@ -1610,13 +1547,18 @@ void addMemberDocs(Entry *root,MemberDef *md, const char *funcDecl,
// outside it
if ( /* !md->isStatic() && !root->stat && do not replace doc of static */
(
- !md->briefDescription() || /* no docs yet */
- !root->parent->name.isNull() /* member of a class */
+ md->briefDescription().isEmpty() || /* no docs yet */
+ !root->parent->name.isNull() /* member of a class */
) && root->brief.length()>0
)
{
md->setBriefDescription(root->brief);
}
+
+ if (md->bodyCode().isEmpty() && !root->body.isEmpty()) /* no body yet */
+ {
+ md->setBody(root->body);
+ }
}
md->setDefFile(root->fileName);
md->setDefLine(root->startLine);
@@ -1630,13 +1572,13 @@ void addMemberDocs(Entry *root,MemberDef *md, const char *funcDecl,
// function declaration `decl' to the corresponding member definition.
bool findUnrelatedFunction(Entry *root,
- const QString &namespaceName,
+ const QCString &namespaceName,
const char *name,
const char *,
const char *decl)
{
MemberName *mn=0;
- QString n=name;
+ QCString n=name;
if (n.find("::")!=-1) return FALSE; // skip undefined class members
//printf("findUnrelatedFunction(%s)\n",name);
if (n.length()>0 && (mn=functionNameDict[n])) // function name defined
@@ -1646,7 +1588,7 @@ bool findUnrelatedFunction(Entry *root,
while (md)
{
NamespaceDef *nd=md->getNamespace();
- QString nsName = nd ? nd->name().data() : "";
+ QCString nsName = nd ? nd->name().data() : "";
if (namespaceName.length()==0 ||
nsName==namespaceName)
{
@@ -1698,6 +1640,89 @@ bool findUnrelatedFunction(Entry *root,
return TRUE;
}
+void substituteTemplateArgNames(ArgumentList *src,
+ const QCString &s,
+ ArgumentList *tempArgs,
+ ArgumentList *dst)
+{
+ ArgumentListIterator ali(*src);
+ Argument *a=0;
+ for (ali.toFirst();(a=ali.current());++ali) // for each member argument
+ {
+ QCString type=a->type.copy();
+ bool isReplaced=FALSE;
+ QRegExp re(idMask);
+ int i,p=0,l,c=0;
+ while ((i=re.match(s,p,&l))!=-1) // for each template name found at the
+ // member definition
+ {
+ Argument *ta = tempArgs->at(c);
+ if (ta) // get matching template argument of the class
+ {
+ QCString dstName=s.mid(i,l);
+ QCString srcName=ta->type.copy();
+ int bi;
+ if ((bi=srcName.findRev(' '))!=-1) // search for separator
+ {
+ // strip the type specifier (usuall class or typename)
+ srcName=srcName.right(srcName.length()-bi-1);
+ }
+
+ //if (srcName.left(6)=="class ") srcName=srcName.right(srcName.length()-6);
+ //if (srcName.left(9)=="typename ") srcName=srcName.right(srcName.length()-9);
+ //printf("Template Name = `%s' -> `%s'\n",srcName.data(),dstName.data());
+ if (srcName!=dstName) /* we need to substitute */
+ {
+ int ti,tp=0;
+ QCString result;
+ int sl=srcName.length();
+ while ((ti=type.find(srcName,tp))!=-1)
+ {
+ result+=type.mid(tp,ti-tp);
+ if (
+ (ti==0 || !isId(type.at(ti-1))) &&
+ (ti+sl==(int)type.length() || !isId(type.at(ti+sl)))
+ ) /* idenitifier -> replace */
+ {
+ result+=dstName;
+ }
+ else /* substring of an identifier */
+ {
+ result+=srcName;
+ }
+ tp=ti+sl;
+ }
+ result+=type.right(type.length()-tp);
+ type=result;
+ isReplaced = TRUE;
+ }
+ }
+ p=i+l;
+ c++;
+ }
+ Argument *na = new Argument(*a);
+ if (isReplaced)
+ {
+ //printf("Template Arg: `%s' -> `%s'\n",na->type.data(),type.data());
+ na->type=type;
+ }
+ else
+ {
+ //printf("Template Arg `%s' not changed\n",a->type.data());
+ }
+ dst->append(na);
+ }
+ //printf("substituteTemplateArgNames(src=`%s',tempNameStr=`%s',tempArgs=`%s',dest=`%s')\n",
+ // argListToString(src).data(),
+ // s.data(),
+ // argListToString(tempArgs).data(),
+ // argListToString(dst).data()
+ // );
+ dst->constSpecifier = src->constSpecifier;
+ dst->volatileSpecifier = src->volatileSpecifier;
+ dst->pureSpecifier = src->pureSpecifier;
+
+}
//----------------------------------------------------------------------
// This function tries to find a member (in a documented class/file/namespace)
@@ -1710,23 +1735,28 @@ bool findUnrelatedFunction(Entry *root,
// The boolean overloaded is used to specify whether or not a standard
// overload documentation line should be generated.
-void findMember(Entry *root,QString funcDecl,QString related,bool overloaded,
+void findMember(Entry *root,QCString funcDecl,QCString related,bool overloaded,
bool isFunc)
{
Debug::print(Debug::FindMembers,0,
- "findMember(root=%p,funcDecl=`%s',related=`%s',overload=%d,isFunc=%d)\n",
- root,funcDecl.data(),related.data(),overloaded,isFunc
+ "findMember(root=%p,funcDecl=`%s',related=`%s',overload=%d,isFunc=%d\n====\ndoc=%s\n====\n)\n",
+ root,funcDecl.data(),related.data(),overloaded,isFunc,root->doc.data()
);
+ if (Config::includeSourceFlag && !root->body.isEmpty())
+ {
+ //printf("Function: %s\n-----------------\n%s\n------------------\n",
+ //root->name.data(),root->body.data());
+ }
- QString scopeName;
- QString className;
- QString namespaceName;
- QString classTempList;
- QString funcType;
- QString funcName;
- QString funcArgs;
- QString funcTempList;
- QString exceptions;
+ QCString scopeName;
+ QCString className;
+ QCString namespaceName;
+ QCString classTempList;
+ QCString funcType;
+ QCString funcName;
+ QCString funcArgs;
+ QCString funcTempList;
+ QCString exceptions;
bool isRelated=FALSE;
bool isFriend=FALSE;
@@ -1764,7 +1794,8 @@ void findMember(Entry *root,QString funcDecl,QString related,bool overloaded,
// if a related class name is specified and the class name could
// not be derived from the function declaration, then use the
// related field.
- //printf("scopeName=`%s' className=`%s'\n",scopeName.data(),className.data());
+ //printf("scopeName=`%s' classTempList=`%s' className=`%s'\n",
+ // scopeName.data(),classTempList.data(),className.data());
if (/*scopeName.isEmpty() &&*/ !related.isEmpty() && !isRelated)
{
isRelated=TRUE;
@@ -1805,6 +1836,41 @@ void findMember(Entry *root,QString funcDecl,QString related,bool overloaded,
}
}
+ // see if (part of) the scope name is a namespace name
+ extractNamespaceName(scopeName,className,namespaceName);
+
+ QCString tempScopeName=scopeName.copy();
+ int ti;
+ int spi = namespaceName.isEmpty() ? 0 : namespaceName.length()+2;
+ if ((ti=tempScopeName.find("::",spi))!=-1 && !classTempList.isEmpty())
+ {
+ // insert template parameters after the first scope name
+ tempScopeName=tempScopeName.left(ti)+classTempList+
+ tempScopeName.right(tempScopeName.length()-ti);
+ }
+ else
+ {
+ tempScopeName+=classTempList;
+ }
+
+
+ if (root->tArgList==0 && !classTempList.isEmpty())
+ {
+ // no template specifiers found during parsing (because \fn was used),
+ // but there are template names in the scope, so we build the template
+ // specifiers from that.
+ root->tArgList = new ArgumentList;
+ QRegExp re(idMask);
+ int i,p=0,l;
+ while ((i=re.match(classTempList,p,&l))!=-1) // for each template name found
+ {
+ Argument *a = new Argument;
+ a->type = "class "+classTempList.mid(i,l);
+ root->tArgList->append(a);
+ p=i+l;
+ }
+ }
+
//printf("scopeName=`%s' className=`%s'\n",scopeName.data(),className.data());
// rebuild the function declaration (needed to get the scope right).
if (scopeName.length()>0 && !isRelated && !isFriend)
@@ -1813,22 +1879,22 @@ void findMember(Entry *root,QString funcDecl,QString related,bool overloaded,
{
if (isFunc) // a function -> we use argList for the arguments
{
- funcDecl=funcType+" "+scopeName+classTempList+"::"+funcName+funcTempList;
+ funcDecl=funcType+" "+tempScopeName+"::"+funcName+funcTempList;
}
else
{
- funcDecl=funcType+" "+scopeName+classTempList+"::"+funcName+funcArgs;
+ funcDecl=funcType+" "+tempScopeName+"::"+funcName+funcArgs;
}
}
else
{
if (isFunc) // a function => we use argList for the arguments
{
- funcDecl=scopeName+classTempList+"::"+funcName+funcTempList;
+ funcDecl=tempScopeName+"::"+funcName+funcTempList;
}
else // variable => add `argument' list
{
- funcDecl=scopeName+classTempList+"::"+funcName+funcArgs;
+ funcDecl=tempScopeName+"::"+funcName+funcArgs;
}
}
}
@@ -1858,12 +1924,10 @@ void findMember(Entry *root,QString funcDecl,QString related,bool overloaded,
}
}
- QString fullFuncDecl=funcDecl.copy();
+ QCString fullFuncDecl=funcDecl.copy();
if (isFunc) fullFuncDecl+=argListToString(root->argList);
//printf("scopeName=`%s' className=`%s'\n",scopeName.data(),className.data());
- // see if (part of) the scope name is a namespace name
- extractNamespaceName(scopeName,className,namespaceName);
//printf("scopeName=`%s' className=`%s'\n",scopeName.data(),className.data());
// destructor => do backward class name substitution if needed
@@ -1902,11 +1966,11 @@ void findMember(Entry *root,QString funcDecl,QString related,bool overloaded,
if (className.length()>0) // class name is valid
{
int count=0;
- MemberDef *md=mn->first();
+ MemberDef *md=mn->first(); // for each member with that name
while (md)
{
ClassDef *cd=md->memberClass();
- //printf("Member %s member className=%s this className=%s\n",md->name().data(),cd->name().data(),className.data());
+ //printf("Member %s (member scopeName=%s) (this scopeName=%s) classTempList=%s\n",md->name().data(),cd->name().data(),scopeName.data(),classTempList.data());
ClassDef *tcd=0;
if (classTempList.length()>0) // try to find the correct specialization
{
@@ -1917,15 +1981,60 @@ void findMember(Entry *root,QString funcDecl,QString related,bool overloaded,
{
tcd=getClass(scopeName);
}
- //printf("tcd=%p\n",tcd);
- if (cd && tcd==cd)
+ if (cd && tcd==cd) // member's classes match
{
- //printf("Class %s\n",cd->name().data());
+ int ci;
+ ArgumentList *classTemplArgs = cd->templateArguments();
+ if ((ci=cd->name().find("::"))!=-1) // nested class
+ {
+ ClassDef *parentClass = getClass(cd->name().left(ci));
+ if (parentClass)
+ classTemplArgs = parentClass->templateArguments();
+ }
+ //printf("cd->name=%s classTemplArgs=%s\n",cd->name().data(),
+ // argListToString(classTemplArgs).data());
+ ArgumentList *argList = 0;
+ bool substDone=FALSE;
+ if (!classTempList.isEmpty() &&
+ classTemplArgs &&
+ md->argumentList()
+ )
+ {
+ /* the function definition has template arguments
+ * and the class also has template arguments, so
+ * we must substitute the template names if they are
+ * different before doing the match
+ */
+ argList = new ArgumentList;
+ argList->setAutoDelete(TRUE);
+ substituteTemplateArgNames(
+ md->argumentList(), /* source argument list */
+ classTempList, /* template names source */
+ classTemplArgs, /* template names dest */
+ argList /* dest argument list */
+ );
+ substDone=TRUE;
+ }
+ else /* no template arguments, compare argument lists directly */
+ {
+ argList = md->argumentList();
+ }
bool matching=
md->isVariable() || md->isTypedef() || // needed for function pointers
(md->argumentList()==0 && root->argList->count()==0) ||
- matchArguments(md->argumentList(), root->argList,
- className,namespaceName);
+ matchArguments(argList, root->argList,className,namespaceName);
+
+ if (substDone) // found a new argument list
+ {
+ //printf("root->tArgList=`%s'\n",argListToString(root->tArgList).data());
+ if (matching) // replace member's argument list
+ {
+ md->setScopeTemplateArguments(root->tArgList);
+ md->setArgumentList(argList);
+ }
+ else // no match -> delete argument list
+ delete argList;
+ }
if (matching)
{
addMemberDocs(root,md,funcDecl,overloaded);
@@ -1975,7 +2084,7 @@ void findMember(Entry *root,QString funcDecl,QString related,bool overloaded,
ASSERT(md);
ClassDef *cd=md->memberClass();
ASSERT(cd);
- QString className=cd->name().copy();
+ QCString className=cd->name().copy();
md=mn->next();
bool unique=TRUE;
while (md)
@@ -1997,7 +2106,7 @@ void findMember(Entry *root,QString funcDecl,QString related,bool overloaded,
mtype,root->tArgList,root->argList);
md->setMemberClass(cd);
md->setDefinition(funcDecl);
- QString doc=getOverloadDocs();
+ QCString doc=getOverloadDocs();
doc+="<p>";
doc+=root->doc;
md->setDocumentation(doc);
@@ -2007,6 +2116,7 @@ void findMember(Entry *root,QString funcDecl,QString related,bool overloaded,
md->setDefLine(root->startLine);
md->setPrototype(root->proto);
md->addSectionsToDefinition(root->anchors);
+ md->setBody(root->body);
mn->inSort(md);
cd->insertMember(md);
cd->insertUsedFile(root->fileName);
@@ -2071,6 +2181,7 @@ void findMember(Entry *root,QString funcDecl,QString related,bool overloaded,
md->setDefFile(root->fileName);
md->setDefLine(root->startLine);
md->setPrototype(root->proto);
+ md->setBody(root->body);
md->addSectionsToDefinition(root->anchors);
mn->inSort(md);
cd->insertMember(md);
@@ -2118,8 +2229,8 @@ void findMemberDocumentation(Entry *root)
int i,l;
QRegExp re("([a-zA-Z0-9: ]*\\*+[ \\*]*");
Debug::print(Debug::FindMembers,0,
- "root->type=`%s' root->name=`%s' root->args=`%s'\n",
- root->type.data(),root->name.data(),root->args.data()
+ "root->type=`%s' root->name=`%s' root->args=`%s' section=%x\n",
+ root->type.data(),root->name.data(),root->args.data(),root->section
);
bool isFunc=TRUE;
if ((i=re.match(root->type,0,&l))!=-1) // func variable/typedef to func ptr
@@ -2151,8 +2262,12 @@ void findMemberDocumentation(Entry *root)
//printf("Overloaded member %s found\n",root->name.data());
findMember(root,root->name,root->relates,TRUE,isFunc);
}
- else if (root->section==Entry::FUNCTION_SEC &&
- (root->doc.length()>0 || root->brief.length()>0 || extractAllFlag))
+ else if
+ (root->section==Entry::FUNCTION_SEC &&
+ (!root->doc.isEmpty() || !root->brief.isEmpty() ||
+ !root->body.isEmpty() /*|| Config::extractAllFlag*/
+ )
+ )
{
//printf("Documentation for member `%s' found args=`%s' excp=`%s'\n",
// root->name.data(),root->args.data(),root->exception.data());
@@ -2179,6 +2294,10 @@ void findMemberDocumentation(Entry *root)
//if (root->relates.length()>0) printf(" Relates %s\n",root->relates.data());
findMember(root,root->name,root->relates,FALSE,FALSE);
}
+ else
+ {
+ // skip section
+ }
EntryListIterator eli(*root->sublist);
Entry *e;
for (;(e=eli.current());++eli)
@@ -2195,31 +2314,31 @@ void findEnums(Entry *root)
if (root->section==Entry::ENUM_SEC)
// non anonymous enumeration
{
- MemberDef *md=0;
- ClassDef *cd=0;
- FileDef *fd=0;
- NamespaceDef *nd=0;
+ MemberDef *md=0;
+ ClassDef *cd=0;
+ FileDef *fd=0;
+ NamespaceDef *nd=0;
MemberNameDict *mnd=0;
MemberNameList *mnl=0;
bool isGlobal;
//printf("Found enum with name `%s'\n",root->name.data());
int i;
- QString name;
+ QCString name;
if ((i=root->name.findRev("::"))!=-1) // scope is specified
{
- QString scope=root->name.left(i); // extract scope
+ QCString scope=root->name.left(i); // extract scope
name=root->name.right(root->name.length()-i-2); // extract name
- cd=getClass(scope);
- if (!cd) nd=namespaceDict[scope];
+ if ((cd=getClass(scope))==0) nd=namespaceDict[scope];
}
else // no scope, check the scope in which the docs where found
{
- if (( root->parent->section & Entry::COMPOUND_MASK )
+ if (( root->parent->section & Entry::SCOPE_MASK )
&& root->parent->name.length()>0
) // found enum docs inside a compound
{
- cd=getClass(root->parent->name);
+ QCString scope=root->parent->name;
+ if ((cd=getClass(scope))==0) nd=namespaceDict[scope];
}
name=root->name.copy();
}
@@ -2231,7 +2350,7 @@ void findEnums(Entry *root)
mnl=&memberNameList;
isGlobal=FALSE;
}
- else if (nd) // found enum inside namespace
+ else if (nd && !nd->name().isEmpty() && nd->name().at(0)!='@') // found enum inside namespace
{
mnd=&functionNameDict;
mnl=&functionNameList;
@@ -2254,7 +2373,7 @@ void findEnums(Entry *root)
md->setDefFile(root->fileName);
md->setDefLine(root->startLine);
md->addSectionsToDefinition(root->anchors);
- if (nd)
+ if (nd && !nd->name().isEmpty() && nd->name().at(0)!='@')
{
md->setDefinition(nd->name()+"::"+name);
nd->insertMember(md);
@@ -2299,12 +2418,12 @@ void findEnums(Entry *root)
// get list of members with the same name as the field
{
MemberDef *fmd=fmn->first();
- while (fmd) // search for the class with the right name
+ while (fmd) // search for the scope with the right name
{
- if (nd)
+ if (nd && !nd->name().isEmpty() && nd->name().at(0)!='@')
{
NamespaceDef *fnd=fmd->getNamespace();
- if (fnd==nd)
+ if (fnd==nd) // enum value is inside a namespace
{
md->insertEnumField(fmd);
fmd->setEnumScope(md);
@@ -2313,7 +2432,7 @@ void findEnums(Entry *root)
else if (isGlobal)
{
FileDef *ffd=fmd->getFileDef();
- if (ffd==fd)
+ if (ffd==fd) // enum value has file scope
{
md->insertEnumField(fmd);
fmd->setEnumScope(md);
@@ -2322,7 +2441,7 @@ void findEnums(Entry *root)
else
{
ClassDef *fcd=fmd->memberClass();
- if (fcd==cd)
+ if (fcd==cd) // enum value is inside a class
{
md->insertEnumField(fmd); // add field def to list
fmd->setEnumScope(md); // cross ref with enum name
@@ -2358,10 +2477,10 @@ void findEnumDocumentation(Entry *root)
//printf("Found docs for enum with name `%s'\n",root->name.data());
int i;
ClassDef *cd=0;
- QString name;
+ QCString name;
if ((i=root->name.findRev("::"))!=-1) // scope is specified
{
- QString scope=root->name.left(i); // extract scope
+ QCString scope=root->name.left(i); // extract scope
name=root->name.right(root->name.length()-i-2); // extract name
cd=getClass(scope);
//printf("Scope=`%s' Name=`%s'\n",scope.data(),name.data());
@@ -2382,7 +2501,7 @@ void findEnumDocumentation(Entry *root)
if (cd)
{
//printf("Enum: scope=`%s' name=`%s'\n",cd->name(),name.data());
- QString className=cd->name().copy();
+ QCString className=cd->name().copy();
MemberName *mn=memberNameDict[name];
if (mn)
{
@@ -2519,29 +2638,30 @@ void computeMemberRelations()
while (mn) // for each member name
{
MemberNameIterator mdi(*mn);
- for ( ; mdi.current() ; ++mdi) // for each function with a specific name
+ for ( ; mdi.current() ; ++mdi) // for each member with a specific arg list
{
MemberDef *md=mdi.current();
MemberNameIterator bmdi(*mn);
- for ( ; bmdi.current() ; ++bmdi) // for each other function with that name
+ for ( ; bmdi.current() ; ++bmdi) // for each other member with that signature
{
MemberDef *bmd=bmdi.current();
- if (md!=bmd && bmd->memberClass() && md->memberClass() &&
- isBaseClass(bmd->memberClass(),md->memberClass()))
+ ClassDef *bmcd = bmd->memberClass();
+ ClassDef *mcd = md->memberClass();
+ //printf("Check relation between `%s'::`%s' and `%s'::`%s'\n",
+ // mcd->name().data(),md->name().data(),
+ // bmcd->name().data(),bmd->name().data()
+ // );
+ if (md!=bmd && bmcd && mcd && isBaseClass(bmcd,mcd))
{
- //printf("Checking Base: %s\nWith normal : %s\n",bmd->definition(),md->definition());
- if (/*matchArguments(bmd->argsString(),md->argsString())*/
- matchArguments(bmd->argumentList(),md->argumentList())
- )
+ //printf(" Base argList=`%s'\n Super argList=`%s'\n",
+ // argListToString(bmd->argumentList()).data(),
+ // argListToString(md->argumentList()).data()
+ // );
+ if ( matchArguments(bmd->argumentList(),md->argumentList()) )
{
- //printf("Base: %s\nNorm: %s\n",bmd->definition(),md->definition());
- ClassDef *bmcd = bmd->memberClass();
- ClassDef *mcd = md->memberClass();
+ //printf(" match found!\n");
if (mcd && bmcd &&
- (bmcd->protection()!=Private || extractPrivateFlag) &&
- (bmcd->hasDocumentation() || !hideClassFlag) &&
- (mcd->protection()!=Private || extractPrivateFlag) &&
- (mcd->hasDocumentation() || !hideClassFlag)
+ mcd->isVisibleExt() && bmcd->isVisibleExt()
)
{
md->setReimplements(bmd);
@@ -2564,7 +2684,7 @@ void mergeMembers(ClassDef *cd,BaseClassList *bcl)
//if (mcd->flag==TRUE)
//{
// err("Error: Cyclic inhertance dependency found for class %s\n",mcd->name());
- // return;
+ // return;
//}
//mcd->flag=TRUE;
@@ -2618,6 +2738,7 @@ void mergeMembers(ClassDef *cd,BaseClassList *bcl)
found =
/*matchArguments(srcMd->argsString(),dstMd->argsString());*/
matchArguments(srcMd->argumentList(),dstMd->argumentList());
+ ambigue=!found;
}
else // member is in a non base class => multiple inheritance
// using the same base class.
@@ -2627,7 +2748,7 @@ void mergeMembers(ClassDef *cd,BaseClassList *bcl)
// dstMd->name().data(),
// dstMi->scopePath.left(dstMi->scopePath.find("::")+2).data());
- QString scope=dstMi->scopePath.left(dstMi->scopePath.find("::")+2);
+ QCString scope=dstMi->scopePath.left(dstMi->scopePath.find("::")+2);
if (scope!=dstMi->ambiguityResolutionScope.left(scope.length()))
dstMi->ambiguityResolutionScope.prepend(scope);
ambigue=TRUE;
@@ -2648,7 +2769,7 @@ void mergeMembers(ClassDef *cd,BaseClassList *bcl)
// dstMd->name().data(),
// dstMi->scopePath.left(dstMi->scopePath.find("::")+2).data());
- QString scope=dstMi->scopePath.left(dstMi->scopePath.find("::")+2);
+ QCString scope=dstMi->scopePath.left(dstMi->scopePath.find("::")+2);
if (scope!=dstMi->ambiguityResolutionScope.left(scope.length()))
dstMi->ambiguityResolutionScope.prepend(scope);
ambigue=TRUE;
@@ -2660,7 +2781,6 @@ void mergeMembers(ClassDef *cd,BaseClassList *bcl)
Specifier virt=srcMi->virt;
if (srcMi->virt==Normal && bcd->virt!=Normal) virt=bcd->virt;
MemberInfo *newMi = new MemberInfo(srcMd,bcd->prot,virt);
- //if (srcMi->memberDef->memberClass()!=bClass)
newMi->scopePath=bClass->name()+"::"+srcMi->scopePath;
if (ambigue)
{
@@ -2669,7 +2789,7 @@ void mergeMembers(ClassDef *cd,BaseClassList *bcl)
// srcMd->name().data(),
// bClass->name().data());
- QString scope=bClass->name().copy(); scope+="::";
+ QCString scope=bClass->name().copy(); scope+="::";
if (scope!=srcMi->ambiguityResolutionScope.left(scope.length()))
newMi->ambiguityResolutionScope=
scope+srcMi->ambiguityResolutionScope;
@@ -2764,7 +2884,8 @@ void generateFileDocs()
void generateClassDocs()
{
// write the installdox script if necessary
- if (generateHtml && (tagFileList.count()>0 || searchEngineFlag))
+ if (Config::generateHtml &&
+ (Config::tagFileList.count()>0 || Config::searchEngineFlag))
writeInstallScript();
msg("Generating index page...\n");
@@ -2797,8 +2918,8 @@ void generateClassDocs()
if (!cd->isReference() &&
//!cd->name().isEmpty() &&
//cd->name().at(0)!='@' &&
- //(cd->protection()!=Private || extractPrivateFlag) &&
- //(cd->hasDocumentation() || !hideClassFlag)
+ //(cd->protection()!=Private || Config::extractPrivateFlag) &&
+ //(cd->hasDocumentation() || !Config::hideClassFlag)
cd->isVisible()
)
// skip external references and anonymous compounds
@@ -2807,7 +2928,7 @@ void generateClassDocs()
cd->writeDocumentation(*outputList);
cd->writeMemberList(*outputList);
- if (verbatimHeaderFlag) cd->writeIncludeFile(*outputList);
+ if (Config::verbatimHeaderFlag) cd->writeIncludeFile(*outputList);
}
}
}
@@ -2912,31 +3033,33 @@ void buildPageList(Entry *root)
}
else
{
- QString baseName=root->name.copy();
+ QCString baseName=root->name.copy();
if (baseName.right(4)==".tex")
baseName=baseName.left(baseName.length()-4);
else if (baseName.right(5)==".html")
baseName=baseName.left(baseName.length()-5);
pi=new PageInfo(baseName, root->doc,
root->args.stripWhiteSpace());
- setFileNameForSections(root->anchors,root->name);
+ QCString pageName;
+ if (Config::caseSensitiveNames)
+ pageName=pi->name.copy();
+ else
+ pageName=pi->name.lower();
+ setFileNameForSections(root->anchors,pageName);
+
pageList.append(pi);
pageDict.insert(baseName,pi);
if (pi->title.length()>0)
{
- QString pageName;
- if (caseSensitiveNames)
- pageName=pi->name.copy();
- else
- pageName=pi->name.lower();
//outputList->writeTitle(pi->name,pi->title);
// a page name is a label as well!
SectionInfo *si=new SectionInfo(
pi->name,pi->title,SectionInfo::Section);
si->fileName=pageName+".html";
+ //printf(" SectionInfo: sec=%p sec->fileName=%s\n",si,si->fileName.data());
//printf("Adding section info %s\n",pi->name.data());
- sectionDict.insert(pi->name,si);
+ sectionDict.insert(pageName,si);
}
}
}
@@ -2979,8 +3102,8 @@ void generatePageDocs()
{
msg("Generating docs for page %s...\n",pi->name.data());
outputList->disable(OutputGenerator::Man);
- QString pageName;
- if (caseSensitiveNames)
+ QCString pageName;
+ if (Config::caseSensitiveNames)
pageName=pi->name.copy();
else
pageName=pi->name.lower();
@@ -3047,7 +3170,7 @@ void generateExampleDocs()
while (pi)
{
msg("Generating docs for example %s...\n",pi->name.data());
- QString n=convertSlashes(pi->name,TRUE)+"-example";
+ QCString n=convertSlashes(pi->name,TRUE)+"-example";
startFile(*outputList,n,"Example Documentation");
//outputList->writeTitle(pi->name,pi->name);
parseExample(*outputList,pi->doc+"\n\\include "+pi->name,pi->name);
@@ -3081,37 +3204,64 @@ void generateNamespaceDocs()
NamespaceDef *nd;
for (;(nd=nli.current());++nli)
{
- msg("Generating docs for namespace %s\n",nd->name().data());
- nd->writeDocumentation(*outputList);
+ if ((nd->getReference() || nd->hasDocumentation()) &&
+ !nd->name().isEmpty() && nd->name().at(0)!='@')
+ {
+ msg("Generating docs for namespace %s\n",nd->name().data());
+ nd->writeDocumentation(*outputList);
+ }
}
}
+#if defined(_WIN32)
+static QCString fixSlashes(QCString &s)
+{
+ QCString result;
+ uint i;
+ for (i=0;i<s.length();i++)
+ {
+ switch(s.at(i))
+ {
+ case '/':
+ case '\\':
+ result+="\\\\";
+ break;
+ default:
+ result+=s.at(i);
+ }
+ }
+ return result;
+}
+#endif
+
+
//----------------------------------------------------------------------------
// generate files for the search engine
void generateSearchIndex()
{
- if (searchEngineFlag && generateHtml)
+ if (Config::searchEngineFlag && Config::generateHtml)
{
// create search index
- QString fileName;
- writeSearchButton(htmlOutputDir);
+ QCString fileName;
+ writeSearchButton(Config::htmlOutputDir);
+#if !defined(_WIN32)
// create cgi script
- fileName = htmlOutputDir+"/"+cgiName;
+ fileName = Config::htmlOutputDir+"/"+Config::cgiName;
QFile f(fileName);
if (f.open(IO_WriteOnly))
{
QTextStream t(&f);
t << "#!/bin/sh" << endl
- << "DOXYSEARCH=" << binAbsPath << "/doxysearch" << endl
- << "DOXYPATH=" << docAbsPath << " ";
+ << "DOXYSEARCH=" << Config::binAbsPath << "/doxysearch" << endl
+ << "DOXYPATH=" << Config::docAbsPath << " ";
- char *s=extDocPathList.first();
+ char *s=Config::extDocPathList.first();
while (s)
{
t << s << " ";
- s=extDocPathList.next();
+ s=Config::extDocPathList.next();
}
t << endl
@@ -3121,28 +3271,65 @@ void generateSearchIndex()
<< "else" << endl
<< " echo \"Content-Type: text/html\"" << endl
<< " echo \"\"" << endl
- << " echo \"<H1>Error: $DOXYSEARCH not found. Check cgi script!\"" << endl
+ << " echo \"<h2>Error: $DOXYSEARCH not found. Check cgi script!</h2>\"" << endl
<< "fi" << endl;
f.close();
struct stat stat_struct;
stat(fileName,&stat_struct);
-#if !defined(_WIN32)
chmod(fileName,stat_struct.st_mode|S_IXUSR|S_IXGRP|S_IXOTH);
-#endif
}
else
{
err("Error: Cannot open file %s for writing\n",fileName.data());
}
+#else /* Windows platform */
+ // create cgi program
+ fileName = Config::cgiName.copy();
+ if (fileName.right(4)==".cgi")
+ fileName=fileName.left(fileName.length()-4);
+ fileName+=".c";
+ fileName.prepend(Config::htmlOutputDir+"/");
+ QFile f(fileName);
+ if (f.open(IO_WriteOnly))
+ {
+ QTextStream t(&f);
+ t << "#include <stdio.h>" << endl;
+ t << "#include <stdlib.h>" << endl;
+ t << "#include <process.h>" << endl;
+ t << endl;
+ t << "const char *DOXYSEARCH = \"" <<
+ fixSlashes(Config::binAbsPath) << "\\\\doxysearch.exe\";" << endl;
+ t << "const char *DOXYPATH = \"" <<
+ fixSlashes(Config::docAbsPath) << "\";" << endl;
+ t << endl;
+ t << "int main(void)" << endl;
+ t << "{" << endl;
+ t << " char buf[1024];" << endl;
+ t << " sprintf(buf,\"%s %s\",DOXYSEARCH,DOXYPATH);" << endl;
+ t << " if (system(buf))" << endl;
+ t << " {" << endl;
+ t << " printf(\"Content-Type: text/html\\n\\n\");" << endl;
+ t << " printf(\"<h2>Error: failed to execute %s</h2>\\n\",DOXYSEARCH);" << endl;
+ t << " exit(1);" << endl;
+ t << " }" << endl;
+ t << " return 0;" << endl;
+ t << "}" << endl;
+ f.close();
+ }
+ else
+ {
+ err("Error: Cannot open file %s for writing\n",fileName.data());
+ }
+#endif /* !defined(_WIN32) */
// create config file
- fileName = htmlOutputDir+"/search.cfg";
+ fileName = Config::htmlOutputDir+"/search.cfg";
f.setName(fileName);
if (f.open(IO_WriteOnly))
{
QTextStream t(&f);
- t << docURL << endl << cgiURL << "/" << cgiName << endl;
+ t << Config::docURL << endl << Config::cgiURL << "/" << Config::cgiName << endl;
f.close();
}
else
@@ -3194,7 +3381,7 @@ void generateConfigFile(const char *configFile,bool shortList)
//----------------------------------------------------------------------------
// read and parse a tag file
-bool readLineFromFile(QFile &f,QString &s)
+bool readLineFromFile(QFile &f,QCString &s)
{
char c=0;
s.resize(0);
@@ -3226,7 +3413,12 @@ bool patternMatch(QFileInfo *fi,QStrList *patList)
char *pattern=patList->first();
while (pattern && !found)
{
- found = found || QDir::match(pattern,fi->fileName());
+#if defined(_WIN32) // windows
+ QRegExp re(pattern,FALSE,TRUE); // case insensitive match
+#else // unix
+ QRegExp re(pattern,TRUE,TRUE); // case sensitive match
+#endif
+ found = found || re.match(fi->fileName())!=-1;
pattern=patList->next();
}
}
@@ -3245,7 +3437,7 @@ void copyAndFilterFile(const char *fileName,BufStr &dest)
QFileInfo fi(fileName);
if (!fi.exists()) return;
- if (inputFilter.isEmpty())
+ if (Config::inputFilter.isEmpty())
{
QFile f(fileName);
if (!f.open(IO_ReadOnly))
@@ -3266,11 +3458,11 @@ void copyAndFilterFile(const char *fileName,BufStr &dest)
{
int c;
// char *p=dest;
- QString cmd=inputFilter+" "+fileName;
+ QCString cmd=Config::inputFilter+" "+fileName;
FILE *f=popen(cmd,"r");
if (!f)
{
- err("Error: could not execute filter %s\n",inputFilter.data());
+ err("Error: could not execute filter %s\n",Config::inputFilter.data());
return;
}
while ((c=fgetc(f))!=EOF) dest.addChar(c),size++;
@@ -3295,17 +3487,17 @@ void copyAndFilterFile(const char *fileName,BufStr &dest)
void readFiles(BufStr &output)
{
- QString *s=inputFiles.first();
+ QCString *s=inputFiles.first();
// char *p=output.data();
while (s)
{
- QString fileName=*s;
+ QCString fileName=*s;
//int fileSize=fi->fileInfo()->size();
int fileNameSize=fileName.length();
//int streamLength=fileSize+fileNameSize+4;
- //QString fileText(streamLength);
+ //QCString fileText(streamLength);
// add begin filename marker
// *p++=0x06;
@@ -3320,7 +3512,7 @@ void readFiles(BufStr &output)
output.addChar(0x06);
// *p++='\n'; // to make ^ work while scanning the first line of a file!
output.addChar('\n');
- if (preprocessingFlag)
+ if (Config::preprocessingFlag)
{
msg("Preprocessing %s...\n",s->data());
preprocessFile(fileName,output);
@@ -3376,7 +3568,7 @@ int readDir(QFileInfo *fi,
patternMatch(cfi,patList) && !patternMatch(cfi,exclPatList))
{
totalSize+=cfi->size()+cfi->absFilePath().length()+4;
- QString name=cfi->fileName();
+ QCString name=convertToQCString(cfi->fileName());
if (fnDict)
{
FileDef *fd=new FileDef(cfi->dirPath()+"/",name);
@@ -3393,15 +3585,15 @@ int readDir(QFileInfo *fi,
fnDict->insert(name,fn);
}
}
- QString *rs=0;
+ QCString *rs=0;
if (resultList || resultDict)
{
- rs=new QString(cfi->absFilePath());
+ rs=new QCString(cfi->absFilePath());
}
if (resultList) resultList->append(rs);
if (resultDict) resultDict->insert(cfi->absFilePath(),rs);
}
- else if (recursiveFlag && cfi->isDir() && cfi->fileName()!="." &&
+ else if (Config::recursiveFlag && cfi->isDir() && cfi->fileName()!="." &&
cfi->fileName()!="..")
{
cfi->setFile(cfi->absFilePath());
@@ -3417,9 +3609,9 @@ int readDir(QFileInfo *fi,
//----------------------------------------------------------------------------
// read the file with name `name' into a string.
-QString readExampleFile(const char *name)
+QCString readExampleFile(const char *name)
{
- QString example;
+ QCString example;
QFileInfo fi(name);
if (fi.exists())
{
@@ -3477,7 +3669,7 @@ int readFileOrDirectory(const char *s,
{
totalSize+=fi.size()+fi.absFilePath().length()+4; //readFile(&fi,fiList,input);
//fiList->inSort(new FileInfo(fi));
- QString name=fi.fileName();
+ QCString name=convertToQCString(fi.fileName());
if (fnDict)
{
FileDef *fd=new FileDef(fi.dirPath(TRUE)+"/",name);
@@ -3494,10 +3686,10 @@ int readFileOrDirectory(const char *s,
fnDict->insert(name,fn);
}
}
- QString *rs=0;
+ QCString *rs=0;
if (resultList || resultDict)
{
- rs=new QString(fi.absFilePath());
+ rs=new QCString(fi.absFilePath());
}
if (resultList) resultList->append(rs);
if (resultDict) resultDict->insert(fi.absFilePath(),rs);
@@ -3514,11 +3706,11 @@ int readFileOrDirectory(const char *s,
void readFormulaRepository()
{
- QFile f(htmlOutputDir+"/formula.repository");
+ QFile f(Config::htmlOutputDir+"/formula.repository");
if (f.open(IO_ReadOnly)) // open repository
{
QTextStream t(&f);
- QString line;
+ QCString line;
while (!t.eof())
{
line=t.readLine();
@@ -3530,8 +3722,8 @@ void readFormulaRepository()
}
else
{
- QString formName = line.left(se);
- QString formText = line.right(line.length()-se-1);
+ QCString formName = line.left(se);
+ QCString formText = line.right(line.length()-se-1);
Formula *f=new Formula(formText);
formulaList.append(f);
formulaDict.insert(formText,f);
@@ -3627,7 +3819,7 @@ int main(int argc,char **argv)
}
QFileInfo configFileInfo1("Doxyfile"),configFileInfo2("doxyfile");
- QString config;
+ QCString config;
if (optind>=argc)
{
if (configFileInfo1.exists())
@@ -3646,23 +3838,24 @@ int main(int argc,char **argv)
config=fileToString(argv[1]);
parseConfig(config);
+ checkConfig();
/**************************************************************************
* Initialize output generators *
**************************************************************************/
outputList = new OutputList(TRUE);
- if (generateHtml)
+ if (Config::generateHtml)
{
outputList->add(new HtmlGenerator);
HtmlGenerator::init();
}
- if (generateLatex)
+ if (Config::generateLatex)
{
outputList->add(new LatexGenerator);
LatexGenerator::init();
}
- if (generateMan)
+ if (Config::generateMan)
{
outputList->add(new ManGenerator);
ManGenerator::init();
@@ -3674,42 +3867,43 @@ int main(int argc,char **argv)
// gather names of all files in the include path
msg("Searching for include files...\n");
- s=includePath.first();
+ s=Config::includePath.first();
while (s)
{
- readFileOrDirectory(s,0,&includeNameDict,0,&filePatternList,
- &excludePatternList,0,0);
- s=includePath.next();
+ readFileOrDirectory(s,0,&includeNameDict,0,&Config::filePatternList,
+ &Config::excludePatternList,0,0);
+ s=Config::includePath.next();
}
msg("Searching for example files...\n");
- s=examplePath.first();
+ s=Config::examplePath.first();
while (s)
{
- readFileOrDirectory(s,0,&exampleNameDict,0,&filePatternList,
- &excludePatternList,0,0);
- s=examplePath.next();
+ readFileOrDirectory(s,0,&exampleNameDict,0,&Config::filePatternList,
+ &Config::excludePatternList,0,0);
+ s=Config::examplePath.next();
}
msg("Searching for files to exclude\n");
- s=excludeSources.first();
+ s=Config::excludeSources.first();
while (s)
{
- readFileOrDirectory(s,0,0,0,&filePatternList,
+ readFileOrDirectory(s,0,0,0,&Config::filePatternList,
0,0,&excludeNameDict);
- s=excludeSources.next();
+ s=Config::excludeSources.next();
}
msg("Reading input files...\n");
int inputSize=0;
- s=inputSources.first();
+ s=Config::inputSources.first();
while (s)
{
inputSize+=readFileOrDirectory(s,&inputNameList,
&inputNameDict,&excludeNameDict,
- &filePatternList,&excludePatternList,
+ &Config::filePatternList,
+ &Config::excludePatternList,
&inputFiles,0);
- s=inputSources.next();
+ s=Config::inputSources.next();
}
//msg("Input size %d bytes\n",inputSize);
@@ -3732,19 +3926,21 @@ int main(int argc,char **argv)
msg("Reading tag files\n");
- s=tagFileList.first();
+ s=Config::tagFileList.first();
while (s)
{
readTagFile(s);
- s=tagFileList.next();
+ s=Config::tagFileList.next();
}
- QFile *tag =new QFile(genTagFile);
- if (genTagFile.length()>0)
+ QFile *tag =new QFile(Config::genTagFile);
+ if (Config::genTagFile.length()>0)
{
if (!tag->open(IO_WriteOnly))
{
- err("Error: cannot open tag file %s for writing\n",genTagFile.data());
+ err("Error: cannot open tag file %s for writing\n",
+ Config::genTagFile.data()
+ );
exit(1);
}
tagFile.setDevice(tag);
@@ -3756,7 +3952,7 @@ int main(int argc,char **argv)
// Notice: the order of the function calls below is very important!
- if (generateHtml)
+ if (Config::generateHtml)
{
msg("Reading formula repository...\n");
readFormulaRepository();
@@ -3801,7 +3997,6 @@ int main(int argc,char **argv)
msg("Searching for friends...\n");
findFriends();
-
msg("Searching for documented variables...\n");
buildVarList(root);
@@ -3910,31 +4105,31 @@ int main(int argc,char **argv)
outputList->writeStyleInfo(0); // write first part
outputList->disableAllBut(OutputGenerator::Latex);
parseText(*outputList,
- theTranslator->trGeneratedAt(dateToString(TRUE),projectName)
+ theTranslator->trGeneratedAt(dateToString(TRUE),Config::projectName)
);
outputList->writeStyleInfo(1); // write second part
parseText(*outputList,theTranslator->trWrittenBy());
outputList->writeStyleInfo(2); // write third part
parseText(*outputList,
- theTranslator->trGeneratedAt(dateToString(TRUE),projectName)
+ theTranslator->trGeneratedAt(dateToString(TRUE),Config::projectName)
);
outputList->writeStyleInfo(3); // write fourth part
parseText(*outputList,theTranslator->trWrittenBy());
outputList->writeStyleInfo(4); // write last part
outputList->enableAll();
- if (formulaList.count()>0 && generateHtml)
+ if (formulaList.count()>0 && Config::generateHtml)
{
msg("Generating bitmaps for formulas in HTML...\n");
- formulaList.generateBitmaps(htmlOutputDir);
+ formulaList.generateBitmaps(Config::htmlOutputDir);
}
- if (searchEngineFlag || tagFileList.count()>0)
+ if (Config::searchEngineFlag || Config::tagFileList.count()>0)
{
msg("\nNow copy the file\n\n %s\n\nto the directory where the CGI binaries are "
- "located and don't forget to run\n\n",(htmlOutputDir+"/"+cgiName).data());
+ "located and don't forget to run\n\n",(Config::htmlOutputDir+"/"+Config::cgiName).data());
msg(" %s/installdox\n\nto replace any dummy links.\n\n",
- htmlOutputDir.data());
+ Config::htmlOutputDir.data());
}
delete tag;