summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--doc/custcmd.doc26
-rw-r--r--src/commentscan.l62
-rw-r--r--src/doctokenizer.l61
-rw-r--r--src/doxygen.cpp4
-rw-r--r--src/markdown.cpp164
5 files changed, 235 insertions, 82 deletions
diff --git a/doc/custcmd.doc b/doc/custcmd.doc
index 02805da..c6be4c4 100644
--- a/doc/custcmd.doc
+++ b/doc/custcmd.doc
@@ -1,12 +1,12 @@
/******************************************************************************
*
- *
+ *
*
* Copyright (C) 1997-2015 by Dimitri van Heesch.
*
* Permission to use, copy, modify, and distribute this software and its
- * documentation under the terms of the GNU General Public License is hereby
- * granted. No representations are made about the suitability of this software
+ * documentation under the terms of the GNU General Public License is hereby
+ * granted. No representations are made about the suitability of this software
* for any purpose. It is provided "as is" without express or implied warranty.
* See the GNU General Public License for more details.
*
@@ -18,11 +18,11 @@
\tableofcontents{html,latex}
-Doxygen provides a large number of \ref commands "special commands",
+Doxygen provides a large number of \ref commands "special commands",
\ref xmlcmds "XML commands", and \ref htmlcmds "HTML commands".
-that can be used to enhance or structure the documentation inside a comment block.
+that can be used to enhance or structure the documentation inside a comment block.
If you for some reason have a need to define new commands you can do
-so by means of an \e alias definition.
+so by means of an \e alias definition.
The definition of an alias should be specified in the configuration file using
the \ref cfg_aliases "ALIASES" configuration tag.
@@ -32,15 +32,15 @@ The simplest form of an alias is a simple substitution of the form
\verbatim
name=value
\endverbatim
- For example defining the following alias:
+ For example defining the following alias:
\verbatim
- ALIASES += sideeffect="\par Side Effects:\n"
+ ALIASES += sideeffect="\par Side Effects:\n"
\endverbatim
will allow you to
- put the command `\sideeffect` (or `@sideeffect`) in the documentation, which
+ put the command `\sideeffect` (or `@sideeffect`) in the documentation, which
will result in a user-defined paragraph with heading <b>Side Effects:</b>.
-Note that you can put `\n`'s in the value part of an alias to insert newlines
+Note that you cannot put `\n`'s in the value part of an alias to insert newlines
(in the resulting output). You can put `^^` in the value part of an alias to
insert a newline as if a physical newline was in the original file.
@@ -52,7 +52,7 @@ use a double escape (\c \\\\{ and \c \\\\})
Also note that you can redefine existing special commands if you wish.
Some commands, such as \ref cmdxrefitem "\\xrefitem" are designed to be used in
-combination with aliases.
+combination with aliases.
\section custcmd_complex Aliases with arguments
Aliases can also have one or more arguments. In the alias definition you then need
@@ -101,9 +101,9 @@ ALIASES += reminder="\xreflist{reminders,Reminder,Reminders}"
Note that if for aliases with more than one argument a comma is used as a separator,
if you want to put a comma inside the command, you will need to escape it with a backslash,
-i.e.
+i.e.
\verbatim
-\l{SomeClass,Some text\, with an escaped comma}
+\l{SomeClass,Some text\, with an escaped comma}
\endverbatim
given the alias definition of `\l` in the example above.
diff --git a/src/commentscan.l b/src/commentscan.l
index 1923e4d..da8e577 100644
--- a/src/commentscan.l
+++ b/src/commentscan.l
@@ -163,7 +163,7 @@ struct DocCmdMap
static const std::map< std::string, DocCmdMap > docCmdMap =
{
// command name handler function command spacing
- { "_linebr", { &handleLineBr, CommandSpacing::Inline }},
+ { "ilinebr", { &handleLineBr, CommandSpacing::Inline }},
{ "addindex", { &handleAddIndex, CommandSpacing::Invisible }},
{ "addtogroup", { &handleAddToGroup, CommandSpacing::Invisible }},
{ "anchor", { &handleAnchor, CommandSpacing::Invisible }},
@@ -472,7 +472,7 @@ BL [ \t\r]*"\n"
B [ \t]
BS ^(({B}*"//")?)(({B}*"*"+)?){B}*
ATTR ({B}+[^>\n]*)?
-DOCNL "\n"|"\\_linebr"
+DOCNL "\n"|"\\ilinebr"
LC "\\"{B}*"\n"
NW [^a-z_A-Z0-9]
FILESCHAR [a-z_A-Z0-9\x80-\xFF\\:\\\/\-\+@&#]
@@ -505,34 +505,34 @@ RCSTAG "$"{ID}":"[^\n$]+"$"
%x XRefItemParam3
%x FileDocArg1
%x ParamArg1
-%x EnumDocArg1
-%x NameSpaceDocArg1
-%x PackageDocArg1
-%x GroupDocArg1
-%x GroupDocArg2
-%x SectionLabel
-%x SectionTitle
-%x SubpageLabel
-%x SubpageTitle
-%x FormatBlock
-%x LineParam
-%x GuardParam
-%x GuardParamEnd
-%x SkipGuardedSection
-%x SkipInternal
+%x EnumDocArg1
+%x NameSpaceDocArg1
+%x PackageDocArg1
+%x GroupDocArg1
+%x GroupDocArg2
+%x SectionLabel
+%x SectionTitle
+%x SubpageLabel
+%x SubpageTitle
+%x FormatBlock
+%x LineParam
+%x GuardParam
+%x GuardParamEnd
+%x SkipGuardedSection
+%x SkipInternal
%x NameParam
-%x InGroupParam
-%x FnParam
-%x OverloadParam
-%x InheritParam
-%x ExtendsParam
+%x InGroupParam
+%x FnParam
+%x OverloadParam
+%x InheritParam
+%x ExtendsParam
%x ReadFormulaShort
-%x ReadFormulaLong
-%x AnchorLabel
+%x ReadFormulaLong
+%x AnchorLabel
%x HtmlComment
%x SkipLang
-%x CiteLabel
-%x CopyDoc
+%x CiteLabel
+%x CopyDoc
%x GuardExpr
%x CdataSection
%x Noop
@@ -833,7 +833,7 @@ RCSTAG "$"{ID}":"[^\n$]+"$"
<Comment>".."[\.]?/[^ \t\n] { // internal ellipsis
addOutput(yyscanner,yytext);
}
-<Comment>(\n|\\_linebr)({B}*(\n|\\_linebr))+ { // at least one blank line (or blank line command)
+<Comment>(\n|\\ilinebr)({B}*(\n|\\ilinebr))+ { // at least one blank line (or blank line command)
if (yyextra->inContext==OutputXRef)
{
// see bug 613024, we need to put the newlines after ending the XRef section.
@@ -842,7 +842,7 @@ RCSTAG "$"{ID}":"[^\n$]+"$"
for (i=0;i<(yy_size_t)yyleng;)
{
if (yytext[i]=='\n') addOutput(yyscanner,'\n'),i++;
- else if (strcmp(yytext+i,"\\_linebr")==0) addOutput(yyscanner,'\n'),i+=8;
+ else if (strcmp(yytext+i,"\\ilinebr")==0) addOutput(yyscanner,"\\ilinebr"),i+=8;
else i++;
}
}
@@ -852,7 +852,7 @@ RCSTAG "$"{ID}":"[^\n$]+"$"
for (i=0;i<(yy_size_t)yyleng;)
{
if (yytext[i]=='\n') addOutput(yyscanner,'\n'),i++;
- else if (strcmp(yytext+i,"\\_linebr")==0) addOutput(yyscanner,'\n'),i+=8;
+ else if (strcmp(yytext+i,"\\ilinebr")==0) addOutput(yyscanner,"\\ilinebr"),i+=8;
else i++;
}
setOutput(yyscanner,OutputDoc);
@@ -1342,7 +1342,7 @@ RCSTAG "$"{ID}":"[^\n$]+"$"
addOutput(yyscanner,yytext);
BEGIN( Comment );
}
-<SectionTitle>[^\n@\\]*/"\\_linebr" { // end of section title
+<SectionTitle>[^\n@\\]*/"\\ilinebr" { // end of section title
addSection(yyscanner);
addOutput(yyscanner,yytext);
BEGIN( Comment );
@@ -2540,7 +2540,7 @@ static bool handleInternal(yyscan_t yyscanner,const QCString &, const QCStringLi
static bool handleLineBr(yyscan_t yyscanner,const QCString &, const QCStringList &)
{
- addOutput(yyscanner,'\n');
+ addOutput(yyscanner,"\\ilinebr");
return FALSE;
}
diff --git a/src/doctokenizer.l b/src/doctokenizer.l
index b1aa82f..6ea39d9 100644
--- a/src/doctokenizer.l
+++ b/src/doctokenizer.l
@@ -114,6 +114,20 @@ bool doctokenizerYYpopContext()
return TRUE;
}
+QCString extractPartAfterNewLine(const QCString &text)
+{
+ int nl1 = text.findRev('\n');
+ if (nl1!=-1)
+ {
+ return text.mid(nl1+1);
+ }
+ int nl2 = text.findRev("\\ilinebr");
+ if (nl2!=-1)
+ {
+ return text.mid(nl2+8);
+ }
+ return text;
+}
//--------------------------------------------------------------------------
@@ -520,25 +534,23 @@ REFWORD_NOCV {FILEMASK}|{LABELID}|{REFWORD2_NOCV}|{REFWORD3}|{REFWORD4_NOCV}
return TK_LISTITEM;
}
}
-<St_Para>{BLANK}*\n{LISTITEM} { /* list item on next line */
- QCString text=yytext;
- text=text.right(text.length()-text.find('\n')-1);
+<St_Para>{BLANK}*(\n|"\\ilinebr"){LISTITEM} { /* list item on next line */
+ QCString text=extractPartAfterNewLine(yytext);
int dashPos = text.findRev('-');
g_token->isEnumList = text.at(dashPos+1)=='#';
g_token->id = -1;
g_token->indent = computeIndent(text,dashPos);
return TK_LISTITEM;
}
-<St_Para>{BLANK}*\n{MLISTITEM} { /* list item on next line */
+<St_Para>{BLANK}*(\n|"\\ilinebr"){MLISTITEM} { /* list item on next line */
if (!g_markdownSupport || g_insidePre)
{
REJECT;
}
else
{
- QCString text=yytext;
+ QCString text=extractPartAfterNewLine(yytext);
static QRegExp re("[*+]");
- text=text.right(text.length()-text.find('\n')-1);
int markPos = text.findRev(re);
g_token->isEnumList = FALSE;
g_token->id = -1;
@@ -546,17 +558,14 @@ REFWORD_NOCV {FILEMASK}|{LABELID}|{REFWORD2_NOCV}|{REFWORD3}|{REFWORD4_NOCV}
return TK_LISTITEM;
}
}
-<St_Para>{BLANK}*\n{OLISTITEM} { /* list item on next line */
+<St_Para>{BLANK}*(\n|"\\ilinebr"){OLISTITEM} { /* list item on next line */
if (!g_markdownSupport || g_insidePre)
{
REJECT;
}
else
{
- QCString text=yytext;
- int nl=text.findRev('\n');
- int len=text.length();
- text=text.right(len-nl-1);
+ QCString text=extractPartAfterNewLine(yytext);
static QRegExp re("[1-9]");
int digitPos = text.find(re);
int dotPos = text.find('.',digitPos);
@@ -571,11 +580,10 @@ REFWORD_NOCV {FILEMASK}|{LABELID}|{REFWORD2_NOCV}|{REFWORD3}|{REFWORD4_NOCV}
g_token->indent = computeIndent(yytext,dotPos);
return TK_ENDLIST;
}
-<St_Para>{BLANK}*\n{ENDLIST} { /* end list on next line */
- QCString text=yytext;
- text=text.right(text.length()-text.find('\n')-1);
+<St_Para>{BLANK}*(\n|"\\ilinebr"){ENDLIST} { /* end list on next line */
+ QCString text=extractPartAfterNewLine(yytext);
int dotPos = text.findRev('.');
- g_token->indent = computeIndent(text,dotPos);
+ g_token->indent = computeIndent(text,dotPos);
return TK_ENDLIST;
}
<St_Para>"{"{BLANK}*"@link"/{BLANK}+ {
@@ -586,9 +594,9 @@ REFWORD_NOCV {FILEMASK}|{LABELID}|{REFWORD2_NOCV}|{REFWORD3}|{REFWORD4_NOCV}
g_token->name = "inheritdoc";
return TK_COMMAND_AT;
}
-<St_Para>"@_fakenl" { // artificial new line
- yylineno++;
- }
+<St_Para>"@_fakenl" { // artificial new line
+ yylineno++;
+ }
<St_Para>{SPCMD3} {
g_token->name = "_form";
bool ok;
@@ -603,6 +611,8 @@ REFWORD_NOCV {FILEMASK}|{LABELID}|{REFWORD2_NOCV}|{REFWORD3}|{REFWORD4_NOCV}
g_token->paramDir=TokenInfo::Unspecified;
return TK_COMMAND_SEL();
}
+<St_Para>"\\ilinebr" {
+ }
<St_Para>{SPCMD1} |
<St_Para>{SPCMD2} |
<St_Para>{SPCMD5} |
@@ -1367,17 +1377,23 @@ REFWORD_NOCV {FILEMASK}|{LABELID}|{REFWORD2_NOCV}|{REFWORD3}|{REFWORD4_NOCV}
warn(g_fileName,yylineno,"Unexpected character '%s' while looking for section label or title",yytext);
}
-<St_Snippet>[^\n]+ |
-<St_Snippet>[^\n]*\n {
- g_token->name = yytext;
+<St_Snippet>[^\\\n]+ {
+ g_token->name += yytext;
+ }
+<St_Snippet>"\\" {
+ g_token->name += yytext;
+ }
+<St_Snippet>(\n|"\\ilinebr") {
g_token->name = g_token->name.stripWhiteSpace();
- return TK_WORD;
+ return TK_WORD;
}
/* Generic rules that work for all states */
<*>\n {
warn(g_fileName,yylineno,"Unexpected new line character");
}
+<*>"\\ilinebr" {
+ }
<*>[\\@<>&$#%~"=] { /* unescaped special character */
//warn(g_fileName,yylineno,"Unexpected character '%s', assuming command \\%s was meant.",yytext,yytext);
g_token->name = yytext;
@@ -1571,6 +1587,7 @@ void doctokenizerYYsetStateAnchor()
void doctokenizerYYsetStateSnippet()
{
+ g_token->name="";
BEGIN(St_Snippet);
}
diff --git a/src/doxygen.cpp b/src/doxygen.cpp
index f073051..bc8eed7 100644
--- a/src/doxygen.cpp
+++ b/src/doxygen.cpp
@@ -9628,7 +9628,7 @@ static void escapeAliases()
value.mid(in,14)!="\\nosubgrouping"
)
{
- newValue+="\\_linebr ";
+ newValue+="\\ilinebr ";
}
else
{
@@ -9643,7 +9643,7 @@ static void escapeAliases()
while ((in=value.find("^^",p))!=-1)
{
newValue+=value.mid(p,in-p);
- newValue+="\\\\_linebr ";
+ newValue+="\\ilinebr ";
p=in+2;
}
newValue+=value.mid(p,value.length()-p);
diff --git a/src/markdown.cpp b/src/markdown.cpp
index 34a9935..2add54c 100644
--- a/src/markdown.cpp
+++ b/src/markdown.cpp
@@ -52,6 +52,90 @@
#include "message.h"
#include "portable.h"
+#if !defined(NDEBUG)
+#define ENABLE_TRACING
+#endif
+
+#ifdef ENABLE_TRACING
+#define IOSTREAM stdout
+#define DATA_BUFSIZE 20
+#if defined(_WIN32) && !defined(CYGWIN)
+#define PRETTY_FUNC __FUNCSIG__
+#else
+#define PRETTY_FUNC __PRETTY_FUNCTION__
+#endif
+
+class Trace
+{
+ public:
+ Trace(const char *func) : m_func(func)
+ {
+ if (Debug::isFlagSet(Debug::Markdown))
+ {
+ fprintf(IOSTREAM,"> %s\n",func);
+ s_indent++;
+ }
+ }
+ Trace(const char *func,const char *data) : m_func(func)
+ {
+ if (Debug::isFlagSet(Debug::Markdown))
+ {
+ indent();
+ char data_s[DATA_BUFSIZE*2+1] = ""; // worst case each input char outputs 2 chars + 0 terminator.
+ int j=0;
+ if (data)
+ {
+ for (int i=0;i<DATA_BUFSIZE;i++)
+ {
+ char c=data[i];
+ if (c==0) break;
+ else if (c=='\n') { data_s[j++]='\\'; data_s[j++]='n'; }
+ else if (c=='\t') { data_s[j++]='\\'; data_s[j++]='t'; }
+ else if (c=='\r') { data_s[j++]='\\'; data_s[j++]='r'; }
+ else if (c=='\\') { data_s[j++]='\\'; data_s[j++]='\\'; }
+ else data_s[j++]=c;
+ }
+ }
+ data_s[j++]=0;
+ fprintf(IOSTREAM,"> %s data=[%s…]\n",func,data_s);
+ s_indent++;
+ }
+ }
+ ~Trace()
+ {
+ if (Debug::isFlagSet(Debug::Markdown))
+ {
+ s_indent--;
+ indent();
+ fprintf(IOSTREAM,"< %s\n",m_func);
+ }
+ }
+ void trace(const char *fmt,...)
+ {
+ if (Debug::isFlagSet(Debug::Markdown))
+ {
+ indent();
+ fprintf(IOSTREAM,": %s: ",m_func);
+ va_list args;
+ va_start(args,fmt);
+ vfprintf(IOSTREAM, fmt, args);
+ va_end(args);
+ }
+ }
+ private:
+ void indent() { for (int i=0;i<s_indent;i++) fputs(" ",IOSTREAM); }
+ const char *m_func;
+ static int s_indent;
+};
+
+int Trace::s_indent = 0;
+#define TRACE(data) Trace trace_(PRETTY_FUNC,data);
+#define TRACE_MORE(...) trace_.trace(__VA_ARGS__);
+#else
+#define TRACE(data) do {} while(false)
+#define TRACE_MORE(...) do {} while(false)
+#endif
+
//-----------
// is character at position i in data part of an identifier?
@@ -79,15 +163,6 @@
data[i]=='\\' || \
data[i]=='@')
-inline int isNewline(const char *data)
-{
- // plain return
- if (data[0] == '\n') return(1);
- // doxygen return from ^^ in ALIASES
- if (data[0] == '\\' && data[1] == '\\' && data[2] == '_' && data[3] == 'l' && data[4] == 'i' &&
- data[5] == 'n' && data[6] == 'e' && data[7] == 'b' && data[8] == 'r') return(9);
- return(0);
-}
//----------
struct TableCell
@@ -127,9 +202,21 @@ const int codeBlockIndent = 4;
//---------- helpers -------
+// test if the next characters in data represent a new line (which can be character \n or string \ilinebr).
+// returns 0 if no newline is found, or the number of characters that make up the newline if found.
+inline int isNewline(const char *data)
+{
+ // normal newline
+ if (data[0] == '\n') return 1;
+ // artificial new line from ^^ in ALIASES
+ if (data[0] == '\\' && qstrncmp(data+1,"ilinebr",7)==0) return 8;
+ return 0;
+}
+
// escape characters that have a special meaning later on.
static QCString escapeSpecialChars(const QCString &s)
{
+ TRACE(s.data());
if (s.isEmpty()) return "";
bool insideQuote=FALSE;
GrowBuf growBuf;
@@ -155,6 +242,7 @@ static QCString escapeSpecialChars(const QCString &s)
static void convertStringFragment(QCString &result,const char *data,int size)
{
+ TRACE(result.data());
if (size<0) size=0;
result.resize(size+1);
memcpy(result.rawData(),data,size);
@@ -206,6 +294,7 @@ static Alignment markersToAlignment(bool leftMarker,bool rightMarker)
// \manonly..\endmanonly
QCString Markdown::isBlockCommand(const char *data,int offset,int size)
{
+ TRACE(data);
bool openBracket = offset>0 && data[-1]=='{';
bool isEscaped = offset>0 && (data[-1]=='\\' || data[-1]=='@');
if (isEscaped) return QCString();
@@ -260,6 +349,7 @@ QCString Markdown::isBlockCommand(const char *data,int offset,int size)
*/
int Markdown::findEmphasisChar(const char *data, int size, char c, int c_size)
{
+ TRACE(data);
int i = 1;
while (i<size)
@@ -358,6 +448,7 @@ int Markdown::findEmphasisChar(const char *data, int size, char c, int c_size)
/** process single emphasis */
int Markdown::processEmphasis1(const char *data, int size, char c)
{
+ TRACE(data);
int i = 0, len;
/* skipping one symbol if coming from emph3 */
@@ -389,6 +480,7 @@ int Markdown::processEmphasis1(const char *data, int size, char c)
/** process double emphasis */
int Markdown::processEmphasis2(const char *data, int size, char c)
{
+ TRACE(data);
int i = 0, len;
while (i<size)
@@ -420,6 +512,7 @@ int Markdown::processEmphasis2(const char *data, int size, char c)
*/
int Markdown::processEmphasis3(const char *data, int size, char c)
{
+ TRACE(data);
int i = 0, len;
while (i<size)
@@ -477,6 +570,7 @@ int Markdown::processEmphasis3(const char *data, int size, char c)
/** Process ndash and mdashes */
int Markdown::processNmdash(const char *data,int off,int size)
{
+ TRACE(data);
// precondition: data[0]=='-'
int i=1;
int count=1;
@@ -511,6 +605,7 @@ int Markdown::processNmdash(const char *data,int off,int size)
/** Process quoted section "...", can contain one embedded newline */
int Markdown::processQuoted(const char *data,int,int size)
{
+ TRACE(data);
int i=1;
int nl=0;
while (i<size && data[i]!='"' && nl<2)
@@ -532,6 +627,7 @@ int Markdown::processQuoted(const char *data,int,int size)
*/
int Markdown::processHtmlTagWrite(const char *data,int offset,int size,bool doWrite)
{
+ TRACE(data);
if (offset>0 && data[-1]=='\\') return 0; // escaped <
// find the end of the html tag
@@ -616,11 +712,13 @@ int Markdown::processHtmlTagWrite(const char *data,int offset,int size,bool doWr
int Markdown::processHtmlTag(const char *data,int offset,int size)
{
+ TRACE(data);
return processHtmlTagWrite(data,offset,size,true);
}
int Markdown::processEmphasis(const char *data,int offset,int size)
{
+ TRACE(data);
if ((offset>0 && !isOpenEmphChar(-1)) || // invalid char before * or _
(size>1 && data[0]!=data[1] && !(isIdChar(1) || extraChar(1) || data[1]=='[')) || // invalid char after * or _
(size>2 && data[0]==data[1] && !(isIdChar(2) || extraChar(2) || data[2]=='['))) // invalid char after ** or __
@@ -686,6 +784,7 @@ void Markdown::writeMarkdownImage(const char *fmt, bool explicitTitle,
int Markdown::processLink(const char *data,int,int size)
{
+ TRACE(data);
QCString content;
QCString link;
QCString title;
@@ -985,6 +1084,7 @@ int Markdown::processLink(const char *data,int,int size)
/** '`' parsing a code span (assuming codespan != 0) */
int Markdown::processCodeSpan(const char *data, int /*offset*/, int size)
{
+ TRACE(data);
int end, nb = 0, i, f_begin, f_end;
/* counting the number of backticks in the delimiter */
@@ -1059,6 +1159,7 @@ int Markdown::processCodeSpan(const char *data, int /*offset*/, int size)
void Markdown::addStrEscapeUtf8Nbsp(const char *s,int len)
{
+ TRACE(s);
if (Portable::strnstr(s,g_doxy_nsbp,len)==0) // no escape needed -> fast
{
m_out.addStr(s,len);
@@ -1071,10 +1172,12 @@ void Markdown::addStrEscapeUtf8Nbsp(const char *s,int len)
int Markdown::processSpecialCommand(const char *data, int offset, int size)
{
+ TRACE(data);
int i=1;
QCString endBlockName = isBlockCommand(data,offset,size);
if (!endBlockName.isEmpty())
{
+ TRACE_MORE("endBlockName=%s\n",qPrint(endBlockName));
int l = endBlockName.length();
while (i<size-l)
{
@@ -1085,6 +1188,7 @@ int Markdown::processSpecialCommand(const char *data, int offset, int size)
{
//printf("found end at %d\n",i);
addStrEscapeUtf8Nbsp(data,i+1+l);
+ TRACE_MORE("result=%d\n",i+1+l);
return i+1+l;
}
}
@@ -1097,24 +1201,29 @@ int Markdown::processSpecialCommand(const char *data, int offset, int size)
if (c=='[' || c==']' || c=='*' || c=='!' || c=='(' || c==')' || c=='`' || c=='_')
{
m_out.addChar(data[1]);
+ TRACE_MORE("result=2\n");
return 2;
}
else if (c=='-' && size>3 && data[2]=='-' && data[3]=='-') // \---
{
m_out.addStr(&data[1],3);
+ TRACE_MORE("result=4\n");
return 4;
}
else if (c=='-' && size>2 && data[2]=='-') // \--
{
m_out.addStr(&data[1],2);
+ TRACE_MORE("result=3\n");
return 3;
}
}
+ TRACE_MORE("result=0\n");
return 0;
}
void Markdown::processInline(const char *data,int size)
{
+ TRACE(data);
int i=0, end=0;
Action_t action;
while (i<size)
@@ -1139,6 +1248,7 @@ void Markdown::processInline(const char *data,int size)
/** returns whether the line is a setext-style hdr underline */
int Markdown::isHeaderline(const char *data, int size, bool allowAdjustLevel)
{
+ TRACE(data);
int i=0, c=0;
while (i<size && data[i]==' ') i++;
@@ -1172,6 +1282,7 @@ int Markdown::isHeaderline(const char *data, int size, bool allowAdjustLevel)
/** returns TRUE if this line starts a block quote */
bool isBlockQuote(const char *data,int size,int indent)
{
+ TRACE(data);
int i = 0;
while (i<size && data[i]==' ') i++;
if (i<indent+codeBlockIndent) // could be a quotation
@@ -1198,6 +1309,7 @@ bool isBlockQuote(const char *data,int size,int indent)
static int isLinkRef(const char *data,int size,
QCString &refid,QCString &link,QCString &title)
{
+ TRACE(data);
//printf("isLinkRef data={%s}\n",data);
// format: start with [some text]:
int i = 0;
@@ -1287,6 +1399,7 @@ static int isLinkRef(const char *data,int size,
static int isHRuler(const char *data,int size)
{
+ TRACE(data);
int i=0;
if (size>0 && data[size-1]=='\n') size--; // ignore newline character
while (i<size && data[i]==' ') i++;
@@ -1314,6 +1427,7 @@ static int isHRuler(const char *data,int size)
static QCString extractTitleId(QCString &title, int level)
{
+ TRACE(title.data());
//static QRegExp r1("^[a-z_A-Z][a-z_A-Z0-9\\-]*:");
static QRegExp r2("\\{#[a-z_A-Z][a-z_A-Z0-9\\-]*\\}");
int l=0;
@@ -1341,6 +1455,7 @@ static QCString extractTitleId(QCString &title, int level)
int Markdown::isAtxHeader(const char *data,int size,
QCString &header,QCString &id,bool allowAdjustLevel)
{
+ TRACE(data);
int i = 0, end;
int level = 0, blanks=0;
@@ -1399,6 +1514,7 @@ int Markdown::isAtxHeader(const char *data,int size,
static int isEmptyLine(const char *data,int size)
{
+ TRACE(data);
int i=0;
while (i<size)
{
@@ -1419,6 +1535,7 @@ static int isEmptyLine(const char *data,int size)
// such as -, -#, *, +, 1., and <li>
static int computeIndentExcludingListMarkers(const char *data,int size)
{
+ TRACE(data);
int i=0;
int indent=0;
bool isDigit=FALSE;
@@ -1487,6 +1604,7 @@ static int computeIndentExcludingListMarkers(const char *data,int size)
static bool isFencedCodeBlock(const char *data,int size,int refIndent,
QCString &lang,int &start,int &end,int &offset)
{
+ TRACE(data);
// rules: at least 3 ~~~, end of the block same amount of ~~~'s, otherwise
// return FALSE
int i=0;
@@ -1528,6 +1646,7 @@ static bool isFencedCodeBlock(const char *data,int size,int refIndent,
static bool isCodeBlock(const char *data,int offset,int size,int &indent)
{
+ TRACE(data);
//printf("<isCodeBlock(offset=%d,size=%d,indent=%d)\n",offset,size,indent);
// determine the indent of this line
int i=0;
@@ -1604,6 +1723,7 @@ static bool isCodeBlock(const char *data,int offset,int size,int &indent)
*/
int findTableColumns(const char *data,int size,int &start,int &end,int &columns)
{
+ TRACE(data);
int i=0,n=0;
int eol;
// find start character of the table line
@@ -1612,8 +1732,10 @@ int findTableColumns(const char *data,int size,int &start,int &end,int &columns)
start = i;
// find end character of the table line
+ //while (i<size && data[i]!='\n') i++;
+ //eol=i+1;
int j = 0;
- while (i<size && !(j = isNewline(data + i))) i++;
+ while (i<size && (j = isNewline(data + i))==0) i++;
eol=i+j;
i--;
@@ -1645,6 +1767,7 @@ int findTableColumns(const char *data,int size,int &start,int &end,int &columns)
/** Returns TRUE iff data points to the start of a table block */
static bool isTableBlock(const char *data,int size)
{
+ TRACE(data);
int cc0,start,end;
// the first line should have at least two columns separated by '|'
@@ -1683,6 +1806,7 @@ static bool isTableBlock(const char *data,int size)
int Markdown::writeTableBlock(const char *data,int size)
{
+ TRACE(data);
int i=0,j,k;
int columns,start,end,cc;
@@ -1857,7 +1981,7 @@ int Markdown::writeTableBlock(const char *data,int size)
}
// need at least one space on either side of the cell text in
// order for doxygen to do other formatting
- m_out.addStr("> " + cellText + " </" + cellTag + ">");
+ m_out.addStr("> " + cellText + "\\ilinebr </" + cellTag + ">");
}
cellTag = "td";
cellClass = "class=\"markdownTableBody";
@@ -1871,6 +1995,7 @@ int Markdown::writeTableBlock(const char *data,int size)
static int hasLineBreak(const char *data,int size)
{
+ TRACE(data);
int i=0;
int j=0;
// search for end of line and also check if it is not a completely blank
@@ -1887,6 +2012,7 @@ static int hasLineBreak(const char *data,int size)
void Markdown::writeOneLineHeaderOrRuler(const char *data,int size)
{
+ TRACE(data);
int level;
QCString header;
QCString id;
@@ -1939,6 +2065,7 @@ void Markdown::writeOneLineHeaderOrRuler(const char *data,int size)
int Markdown::writeBlockQuote(const char *data,int size)
{
+ TRACE(data);
int l;
int i=0;
int curLevel=0;
@@ -1995,6 +2122,7 @@ int Markdown::writeBlockQuote(const char *data,int size)
int Markdown::writeCodeBlock(const char *data,int size,int refIndent)
{
+ TRACE(data);
int i=0,end;
//printf("writeCodeBlock: data={%s}\n",QCString(data).left(size).data());
m_out.addStr("@verbatim\n");
@@ -2047,12 +2175,13 @@ int Markdown::writeCodeBlock(const char *data,int size,int refIndent)
void Markdown::findEndOfLine(const char *data,int size,
int &pi,int&i,int &end)
{
+ TRACE(data);
// find end of the line
int nb=0;
end=i+1;
//while (end<=size && data[end-1]!='\n')
- int j = 0;
- while (end<=size && !(j = isNewline(data+end-1)))
+ int j=0;
+ while (end<=size && (j=isNewline(data+end-1))==0)
{
// while looking for the end of the line we might encounter a block
// that needs to be passed unprocessed.
@@ -2113,13 +2242,14 @@ void Markdown::findEndOfLine(const char *data,int size,
end++;
}
}
- if (j) end += j-1;
+ if (j>0) end+=j-1;
//printf("findEndOfLine pi=%d i=%d end=%d {%s}\n",pi,i,end,QCString(data+i).left(end-i).data());
}
void Markdown::writeFencedCodeBlock(const char *data,const char *lng,
int blockStart,int blockEnd)
{
+ TRACE(data);
QCString lang = lng;
if (!lang.isEmpty() && lang.at(0)=='.') lang=lang.mid(1);
m_out.addStr("@code");
@@ -2134,6 +2264,7 @@ void Markdown::writeFencedCodeBlock(const char *data,const char *lng,
QCString Markdown::processQuotations(const QCString &s,int refIndent)
{
+ TRACE(s.data());
m_out.clear();
const char *data = s.data();
int size = s.length();
@@ -2192,6 +2323,7 @@ QCString Markdown::processQuotations(const QCString &s,int refIndent)
QCString Markdown::processBlocks(const QCString &s,int indent)
{
+ TRACE(s.data());
m_out.clear();
const char *data = s.data();
int size = s.length();
@@ -2333,6 +2465,7 @@ QCString Markdown::processBlocks(const QCString &s,int indent)
/** returns TRUE if input string docs starts with \@page or \@mainpage command */
static bool isExplicitPage(const QCString &docs)
{
+ TRACE(docs.data());
int i=0;
const char *data = docs.data();
if (data)
@@ -2355,6 +2488,7 @@ static bool isExplicitPage(const QCString &docs)
QCString Markdown::extractPageTitle(QCString &docs,QCString &id)
{
+ TRACE(docs.data());
int ln=0;
// first first non-empty line
QCString title;
@@ -2402,6 +2536,7 @@ QCString Markdown::extractPageTitle(QCString &docs,QCString &id)
QCString Markdown::detab(const QCString &s,int &refIndent)
{
+ TRACE(s.data());
int tabSize = Config_getInt(TAB_SIZE);
int size = s.length();
m_out.clear();
@@ -2517,6 +2652,7 @@ QCString Markdown::process(const QCString &input)
QCString markdownFileNameToId(const QCString &fileName)
{
+ TRACE(fileName.data());
QCString baseFn = stripFromPath(QFileInfo(fileName).absFilePath().utf8());
int i = baseFn.findRev('.');
if (i!=-1) baseFn = baseFn.left(i);