Parser for VB.NET - namespaces
James Bursa <[email protected]>
| Newsgroups | gmane.text.doxygen.devel |
|---|---|
| Message-ID | <[email protected]> |
I have started implementing support for VB.NET for Doxygen. The patch and scanner for this are attached. Would there be interest in including this in Doxygen? The generated documentation from this doesn't correctly show namespaces. For example, with this source 1 Namespace N 2 Public Class C 3 Public Sub S() 4 End Sub 5 End Class 6 End Namespace the namespace N is documented as empty and class C has no namespace (with EXTRACT_ALL = YES). The tree of Entry that is being constructed in vbscanner.l contains C as a CLASS_SEC, as a child of N as a NAMESPACE_SEC. What am I doing wrong? James
vbscanner.h
(text/x-c++hdr, 830 B)
#ifndef VBSCANNER_H
#define VBSCANNER_H
#include "parserintf.h"
class VBLanguageScanner : public ParserInterface
{
public:
void parseInput(const char * fileName,
const char *fileBuf,
Entry *root);
bool needsPreprocessing(const QCString &extension);
void parseCode(CodeOutputInterface &codeOutIntf,
const char *scopeName,
const QCString &input,
bool isExampleBlock,
const char *exampleName=0,
FileDef *fileDef=0,
int startLine=-1,
int endLine=-1,
bool inlineFragment=FALSE,
MemberDef *memberDef=0
);
void resetCodeParserState();
void parsePrototype(const char *text);
};
#endif
vbscanner.l
(text/x-csrc, 6.9 KB)
%{
#include <stdio.h>
#include <stdlib.h>
#include <assert.h>
#include <ctype.h>
#include "qtbc.h"
#include <qarray.h>
#include <qstack.h>
#include <qregexp.h>
#include <unistd.h>
#include <qfile.h>
#include <qfileinfo.h>
#include "vbscanner.h"
#include "entry.h"
#include "message.h"
#include "config.h"
#include "doxygen.h"
#include "util.h"
#include "defargs.h"
#include "language.h"
#include "commentscan.h"
#define YY_INPUT(buf, result, max_size) \
result = input_string[input_position] ? \
(buf[0] = input_string[input_position++], 1) : YY_NULL
static const char *input_string;
static size_t input_position;
static const char *input_filename;
static Entry *parent;
static Entry *current;
static void newEntry()
{
parent->addSubEntry(current);
parent = current;
current = new Entry;
initGroupInfo(current);
}
static void end()
{
if (parent->parent)
parent = parent->parent;
}
static const char *after_W(const char *s)
{
size_t space = strcspn(s, " \t");
space += strspn(s + space, " \t");
return s + space;
}
%}
%option case-insensitive
%option never-interactive
%option noyywrap
%option yylineno
%x SUB
W [ \t]+
IDENTIFIER [A-Za-z_][A-Za-z0-9_]*
%%
^([ \t]*'.*\n)+ {
current->doc = yytext;
current->docFile = input_filename;
current->docLine = yylineno;
}
"\""[^"]*"\"" {
}
Class{W}{IDENTIFIER} {
current->section = Entry::CLASS_SEC;
current->type += "Class";
current->name = after_W(yytext);
current->argList->clear();
current->fileName = input_filename;
current->bodyLine = yylineno;
current->startLine = yylineno;
newEntry();
}
End{W}Class\n {
parent->endBodyLine = yylineno;
end();
current->doc = "";
current->docFile = "";
current->docLine = 0;
}
(Sub|Function){W}{IDENTIFIER} {
current->section = Entry::FUNCTION_SEC;
current->type = "";
current->name = after_W(yytext);
current->argList->clear();
current->fileName = input_filename;
current->bodyLine = yylineno;
current->startLine = yylineno;
BEGIN(SUB);
}
<SUB>"("[^)]*")" {
current->args = yytext;
Argument *a = new Argument;
a->name = yytext + 1;
a->name.resize(a->name.length());
current->argList->append(a);
newEntry();
BEGIN(INITIAL);
}
End{W}(Sub|Function)\n {
parent->endBodyLine = yylineno;
end();
current->doc = "";
current->docFile = "";
current->docLine = 0;
}
Public{W} current->protection = Public;
Protected{W} current->protection = Protected;
Private{W} current->protection = Private;
Namespace{W}{IDENTIFIER} {
current->section = Entry::NAMESPACE_SEC;
current->type = "Namespace";
current->name = after_W(yytext);
current->argList->clear();
current->fileName = input_filename;
current->bodyLine = yylineno;
current->startLine = yylineno;
newEntry();
}
End{W}Namespace\n {
parent->endBodyLine = yylineno;
end();
current->doc = "";
current->docFile = "";
current->docLine = 0;
}
Module{W}{IDENTIFIER} {
current->section = Entry::NAMESPACE_SEC;
current->type = "Module";
current->name = after_W(yytext);
current->argList->clear();
current->fileName = input_filename;
current->bodyLine = yylineno;
current->startLine = yylineno;
newEntry();
}
End{W}Module\n {
parent->endBodyLine = yylineno;
end();
current->doc = "";
current->docFile = "";
current->docLine = 0;
}
. ;
\n ;
%%
void VBLanguageScanner::parseInput(const char *fileName, const char *fileBuf, Entry *root)
{
msg("Parsing file %s...\n", fileName);
input_string = fileBuf;
input_position = 0;
input_filename = fileName;
parent = root;
current = new Entry;
current->section = Entry::SOURCE_SEC;
current->name = input_filename;
current->fileName = input_filename;
newEntry();
end();
yylineno = 1;
vbscanYYlex();
}
bool VBLanguageScanner::needsPreprocessing(const QCString &)
{
return false;
}
void VBLanguageScanner::parseCode(CodeOutputInterface &codeOutIntf,
const char *scopeName,
const QCString &input,
bool isExampleBlock,
const char *exampleName,
FileDef *fileDef,
int startLine,
int endLine,
bool inlineFragment,
MemberDef *memberDef
)
{
}
void VBLanguageScanner::parsePrototype(const char *text)
{
}
void VBLanguageScanner::resetCodeParserState()
{
}
//----------------------------------------------------------------------------
#if !defined(YY_FLEX_SUBMINOR_VERSION)
//----------------------------------------------------------------------------
extern "C" { // some bogus code to keep the compiler happy
void vbscannerYYdummy() { yy_flex_realloc(0,0); }
}
#endif
doxygen.patch
(text/x-diff, 806 B)
Index: doxygen.cpp
===================================================================
RCS file: /cvsroot/doxygen/src/doxygen.cpp,v
retrieving revision 1.215
diff -u -d -w -r1.215 doxygen.cpp
--- doxygen.cpp 27 Mar 2006 18:37:02 -0000 1.215
+++ doxygen.cpp 10 Apr 2006 14:14:07 -0000
@@ -66,6 +66,7 @@
#include "parserintf.h"
#include "htags.h"
#include "pyscanner.h"
+#include "vbscanner.h"
#if defined(_MSC_VER) || defined(__BORLANDC__)
#define popen _popen
@@ -8161,6 +8162,7 @@
ParserInterface *defaultParser = new CLanguageScanner;
Doxygen::parserManager = new ParserManager(defaultParser);
Doxygen::parserManager->registerParser(".py",new PythonLanguageScanner);
+ Doxygen::parserManager->registerParser(".vb",new VBLanguageScanner);
// register any additional parsers here...