summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorAdrian Negreanu <groleo@gmail.com>2019-04-11 10:42:06 (GMT)
committerDimitri van Heesch <doxygen@gmail.com>2019-05-04 15:02:03 (GMT)
commit2513172db2942a364e8af4a0d21d0fb2de328af1 (patch)
tree5a24576fd37c6f56a95560a25d10aa990b3cedc3 /src
parent44f678794f5338881620525a5e0fbe25962c7690 (diff)
downloadDoxygen-2513172db2942a364e8af4a0d21d0fb2de328af1.zip
Doxygen-2513172db2942a364e8af4a0d21d0fb2de328af1.tar.gz
Doxygen-2513172db2942a364e8af4a0d21d0fb2de328af1.tar.bz2
declinfo.l: enable reentrant
* put the global variables in struct declinfoYY_state. * globally define yyscanner and declinfo_extra. these two should be per-thread. * add a new yyscan_t function parameter when these functions are referenced: - yyin, yyout, yyextra, yyleng, yytext, yylineno, yycolumn, and yy_flex_debug. - the macros BEGIN, YY_START, YYSTATE, yymore, unput, and yyless - the functions that deal with input buffers: yyrestart - others: yy_switch_to_buffer, yy_create_buffer, yy_delete_buffer, yy_flush_buffer, yypush_buffer_state, yypop_buffer_state, yy_scan_buffer, yy_scan_string, and yy_scan_bytes * add a new yyscan_t function parameter when globals are referenced, to get the yyextra out of the yyscanner.
Diffstat (limited to 'src')
-rw-r--r--src/declinfo.l260
1 files changed, 136 insertions, 124 deletions
diff --git a/src/declinfo.l b/src/declinfo.l
index ade4168..696d000 100644
--- a/src/declinfo.l
+++ b/src/declinfo.l
@@ -18,6 +18,8 @@
%option prefix="declinfoYY"
%option nounput
%option noyywrap
+%option reentrant
+%option extra-type="struct declinfoYY_state *"
%{
@@ -41,30 +43,32 @@
*
* statics
*/
-
-static const char * inputString;
-static int inputPosition;
-static QCString scope;
-static QCString className;
-static QCString classTempList;
-static QCString funcTempList;
-static QCString type;
-static QCString name;
-static QCString args;
-static int sharpCount;
-static bool classTempListFound;
-static bool funcTempListFound;
-static QCString exceptionString;
-static bool insideObjC;
+struct declinfoYY_state
+{
+ const char *inputString;
+ int inputPosition;
+ QCString scope;
+ QCString className;
+ QCString classTempList;
+ QCString funcTempList;
+ QCString type;
+ QCString name;
+ QCString args;
+ int sharpCount;
+ bool classTempListFound;
+ bool funcTempListFound;
+ QCString exceptionString;
+ bool insideObjC;
+};
-static void addType();
-static void addTypeName();
-static int yyread(char *buf,int max_size);
+static void addType(yyscan_t yyscanner);
+static void addTypeName(yyscan_t yyscanner);
+static int yyread(char *buf,int max_size, yyscan_t yyscanner);
/* -----------------------------------------------------------------
*/
#undef YY_INPUT
-#define YY_INPUT(buf,result,max_size) result=yyread(buf,max_size);
+#define YY_INPUT(buf,result,max_size) result=yyread(buf,max_size,yyscanner);
%}
B [ \t]
@@ -83,17 +87,17 @@ ID "$"?([a-z_A-Z\x80-\xFF][a-z_A-Z0-9\x80-\xFF]*)|(@[0-9]+)
%%
<Start>"operator"/({B}*"["{B}*"]")* { // operator rule must be before {ID} rule
- name += yytext;
+ yyextra->name += yytext;
BEGIN(Operator);
}
<Start>{ID}{B}*"("{B}*{ID}{B}*")" { // Objective-C class categories
- if (!insideObjC)
+ if (!yyextra->insideObjC)
{
REJECT;
}
else
{
- name += yytext;
+ yyextra->name += yytext;
}
}
<Start>([~!]{B}*)?{ID}/({B}*"["{B}*"]")* { // the []'s are for Java,
@@ -101,180 +105,188 @@ ID "$"?([a-z_A-Z\x80-\xFF][a-z_A-Z0-9\x80-\xFF]*)|(@[0-9]+)
// dimensional C++ arrays like A[][15]
// the leading ~ is for a destructor
// the leading ! is for a C++/CLI finalizer (see bug 456475 and 635198)
- addTypeName();
- name += yytext;
+ addTypeName(yyscanner);
+ yyextra->name += yytext;
}
-<Start>{B}*"::"{B}* { // found a scope specifier
- if (!scope.isEmpty())
+<Start>{B}*"::"{B}* { // found a yyextra->scope specifier
+ if (!yyextra->scope.isEmpty())
{
- scope+="::"+name; // add name to scope
+ yyextra->scope+="::"+yyextra->name; // add yyextra->name to yyextra->scope
}
else
{
- scope = name.copy(); // scope becomes name
+ yyextra->scope = yyextra->name.copy(); // yyextra->scope becomes yyextra->name
}
- name.resize(0);
+ yyextra->name.resize(0);
}
<Start>{B}*":" { // Objective-C argument separator
- name+=yytext;
+ yyextra->name+=yytext;
}
<Start>[*&]+ {
- addType();
- type+=yytext;
+ addType(yyscanner);
+ yyextra->type+=yytext;
}
<Start>{B}+ {
- addType();
+ addType(yyscanner);
}
<Start>{B}*"("({ID}"::")*{B}*[&*]({B}*("const"|"volatile"){B}+)? {
- addType();
+ addType(yyscanner);
QCString text=yytext;
- type+=text.stripWhiteSpace();
+ yyextra->type+=text.stripWhiteSpace();
}
<Start>{B}*")" {
- type+=")";
+ yyextra->type+=")";
}
<Start>{B}*"(" { // TODO: function pointers
- args+="(";
+ yyextra->args+="(";
BEGIN(ReadArgs);
}
<Start>{B}*"[" {
- args+="[";
+ yyextra->args+="[";
BEGIN(ReadArgs);
}
<Start>{B}*"<" {
- name+="<";
- sharpCount=0;
+ yyextra->name+="<";
+ yyextra->sharpCount=0;
BEGIN(Template);
}
-<Template>"<<" { name+="<<"; }
-<Template>">>" { name+=">>"; }
+<Template>"<<" { yyextra->name+="<<"; }
+<Template>">>" { yyextra->name+=">>"; }
<Template>"<" {
- name+="<";
- sharpCount++;
+ yyextra->name+="<";
+ yyextra->sharpCount++;
}
<Template>">" {
- name+=">";
- if (sharpCount)
- --sharpCount;
+ yyextra->name+=">";
+ if (yyextra->sharpCount)
+ --yyextra->sharpCount;
else
{
BEGIN(Start);
}
}
<Template>. {
- name+=*yytext;
+ yyextra->name+=*yytext;
}
<Operator>{B}*"("{B}*")"{B}*"<>"{B}*/"(" {
- name+="() <>";
+ yyextra->name+="() <>";
BEGIN(ReadArgs);
}
<Operator>{B}*"("{B}*")"{B}*/"(" {
- name+="()";
+ yyextra->name+="()";
BEGIN(ReadArgs);
}
<Operator>[^(]*{B}*("<>"{B}*)?/"(" {
- name+=yytext;
+ yyextra->name+=yytext;
BEGIN(ReadArgs);
}
<ReadArgs>"throw"{B}*"(" {
- exceptionString="throw(";
+ yyextra->exceptionString="throw(";
BEGIN(ReadExceptions);
}
<ReadArgs>. {
- args+=*yytext;
+ yyextra->args+=*yytext;
}
<ReadExceptions>. {
- exceptionString+=*yytext;
+ yyextra->exceptionString+=*yytext;
}
<*>.
<*>\n
%%
-static void addType()
+static void addType(yyscan_t yyscanner)
{
- //printf("addType() type=`%s' scope=`%s' name=`%s'\n",
- // type.data(),scope.data(),name.data());
- if (name.isEmpty() && scope.isEmpty()) return;
- if (!type.isEmpty()) type+=" ";
- if (!scope.isEmpty()) type+=scope+"::";
- type+=name;
- scope.resize(0);
- name.resize(0);
+ struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
+ //printf("addType() yyextra->type=`%s' yyextra->scope=`%s' yyextra->name=`%s'\n",
+ // yyextra->type.data(),yyextra->scope.data(),yyextra->name.data());
+ if (yyextra->name.isEmpty() && yyextra->scope.isEmpty()) return;
+ if (!yyextra->type.isEmpty()) yyextra->type+=" ";
+ if (!yyextra->scope.isEmpty()) yyextra->type+=yyextra->scope+"::";
+ yyextra->type+=yyextra->name;
+ yyextra->scope.resize(0);
+ yyextra->name.resize(0);
}
-static void addTypeName()
+static void addTypeName(yyscan_t yyscanner)
{
- //printf("addTypeName() type=`%s' scope=`%s' name=`%s'\n",
- // type.data(),scope.data(),name.data());
- if (name.isEmpty() ||
- name.at(name.length()-1)==':') // end of Objective-C keyword => append to name not type
+ struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
+ //printf("addTypeName() yyextra->type=`%s' yyextra->scope=`%s' yyextra->name=`%s'\n",
+ // yyextra->type.data(),yyextra->scope.data(),yyextra->name.data());
+ if (yyextra->name.isEmpty() ||
+ yyextra->name.at(yyextra->name.length()-1)==':') // end of Objective-C keyword => append to yyextra->name not yyextra->type
{
return;
}
- if (!type.isEmpty()) type+=' ';
- type+=name;
- name.resize(0);
+ if (!yyextra->type.isEmpty()) yyextra->type+=' ';
+ yyextra->type+=yyextra->name;
+ yyextra->name.resize(0);
}
-static int yyread(char *buf,int max_size)
+static int yyread(char *buf,int max_size, yyscan_t yyscanner)
{
+ struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
int c=0;
- while( c < max_size && inputString[inputPosition] )
+ while( c < max_size && yyextra->inputString[yyextra->inputPosition] )
{
- *buf = inputString[inputPosition++] ;
+ *buf = yyextra->inputString[yyextra->inputPosition++] ;
c++; buf++;
}
return c;
}
-/*@ ----------------------------------------------------------------------------
+/*@ public interface------------------------------------------------------------
*/
+static yyscan_t g_yyscanner;
+static struct declinfoYY_state g_declinfo_extra;
void parseFuncDecl(const QCString &decl,bool objC,QCString &cl,QCString &t,
QCString &n,QCString &a,QCString &ftl,QCString &exc)
{
+ declinfoYYlex_init_extra(&g_declinfo_extra, &g_yyscanner);
+ struct yyguts_t *yyg = (struct yyguts_t*)g_yyscanner;
+
printlex(yy_flex_debug, TRUE, __FILE__, NULL);
- inputString = decl;
- //printf("Input=`%s'\n",inputString);
- if (inputString==0) return;
- inputPosition = 0;
- classTempListFound = FALSE;
- funcTempListFound = FALSE;
- insideObjC = objC;
- scope.resize(0);
- className.resize(0);
- classTempList.resize(0);
- funcTempList.resize(0);
- name.resize(0);
- type.resize(0);
- args.resize(0);
- exceptionString.resize(0);
- // first we try to find the type, scope, name and arguments
- declinfoYYrestart( declinfoYYin );
+ yyextra->inputString = decl;
+ //printf("Input=`%s'\n",yyextra->inputString);
+ if (yyextra->inputString==0) return;
+ yyextra->inputPosition = 0;
+ yyextra->classTempListFound = FALSE;
+ yyextra->funcTempListFound = FALSE;
+ yyextra->insideObjC = objC;
+ yyextra->scope.resize(0);
+ yyextra->className.resize(0);
+ yyextra->classTempList.resize(0);
+ yyextra->funcTempList.resize(0);
+ yyextra->name.resize(0);
+ yyextra->type.resize(0);
+ yyextra->args.resize(0);
+ yyextra->exceptionString.resize(0);
+ // first we try to find the yyextra->type, yyextra->scope, yyextra->name and arguments
+ declinfoYYrestart( yyin, g_yyscanner );
BEGIN( Start );
- declinfoYYlex();
+ declinfoYYlex(g_yyscanner);
- //printf("type=`%s' class=`%s' name=`%s' args=`%s'\n",
- // type.data(),scope.data(),name.data(),args.data());
+ //printf("yyextra->type=`%s' class=`%s' yyextra->name=`%s' yyextra->args=`%s'\n",
+ // yyextra->type.data(),yyextra->scope.data(),yyextra->name.data(),yyextra->args.data());
- int nb = name.findRev('[');
- if (nb!=-1 && args.isEmpty()) // correct for [] in name ambigity (due to Java return type allowing [])
+ int nb = yyextra->name.findRev('[');
+ if (nb!=-1 && yyextra->args.isEmpty()) // correct for [] in yyextra->name ambigity (due to Java return yyextra->type allowing [])
{
- args.prepend(name.right(name.length()-nb));
- name=name.left(nb);
+ yyextra->args.prepend(yyextra->name.right(yyextra->name.length()-nb));
+ yyextra->name=yyextra->name.left(nb);
}
#if 0
{
- int l=scope.length();
+ int l=yyextra->scope.length();
int i=0;
int skipCount=0;
cl.resize(0);
ctl.resize(0);
for (i=0;i<l;i++)
{
- char c=scope.at(i);
+ char c=yyextra->scope.at(i);
if (c=='<')
skipCount++;
else if (c=='>')
@@ -283,12 +295,12 @@ void parseFuncDecl(const QCString &decl,bool objC,QCString &cl,QCString &t,
cl+=c;
}
}
- cl=stripTemplateSpecifiersFromScope(removeRedundantWhiteSpace(scope),FALSE);
+ cl=stripTemplateSpecifiersFromScope(removeRedundantWhiteSpace(yyextra->scope),FALSE);
ctl.resize(0);
#endif
- cl=scope;
- n=removeRedundantWhiteSpace(name);
+ cl=yyextra->scope;
+ n=removeRedundantWhiteSpace(yyextra->name);
int il,ir;
if ((il=n.find('<'))!=-1 && (ir=n.findRev('>'))!=-1)
// TODO: handle cases like where n="operator<< <T>"
@@ -297,18 +309,18 @@ void parseFuncDecl(const QCString &decl,bool objC,QCString &cl,QCString &t,
n=n.left(il);
}
- //ctl=classTempList.copy();
- //ftl=funcTempList.copy();
- t=removeRedundantWhiteSpace(type);
- a=removeRedundantWhiteSpace(args);
- exc=removeRedundantWhiteSpace(exceptionString);
+ //ctl=yyextra->classTempList.copy();
+ //ftl=yyextra->funcTempList.copy();
+ t=removeRedundantWhiteSpace(yyextra->type);
+ a=removeRedundantWhiteSpace(yyextra->args);
+ exc=removeRedundantWhiteSpace(yyextra->exceptionString);
if (!t.isEmpty() && t.at(t.length()-1)==')') // for function pointers
{
a.prepend(")");
t=t.left(t.length()-1);
}
- //printf("type=`%s' class=`%s' name=`%s' args=`%s'\n",
+ //printf("yyextra->type=`%s' class=`%s' yyextra->name=`%s' yyextra->args=`%s'\n",
// t.data(),cl.data(),n.data(),a.data());
printlex(yy_flex_debug, FALSE, __FILE__, NULL);
@@ -325,18 +337,18 @@ void parseFuncDecl(const QCString &decl,bool objC,QCString &cl,QCString &t,
#if 0
void dumpDecl(const char *s)
{
- QCString className;
+ QCString yyextra->className;
QCString classTNames;
- QCString type;
- QCString name;
- QCString args;
+ QCString yyextra->type;
+ QCString yyextra->name;
+ QCString yyextra->args;
QCString funcTNames;
msg("-----------------------------------------\n");
- parseFuncDecl(s,className,classTNames,type,name,args,funcTNames);
- msg("type=`%s' class=`%s' classTempl=`%s' name=`%s' "
- "funcTemplateNames=`%s' args=`%s'\n",
- type.data(),className.data(),classTNames.data(),
- name.data(),funcTNames.data(),args.data()
+ parseFuncDecl(s,yyextra->className,classTNames,yyextra->type,yyextra->name,yyextra->args,funcTNames);
+ msg("yyextra->type=`%s' class=`%s' classTempl=`%s' yyextra->name=`%s' "
+ "funcTemplateNames=`%s' yyextra->args=`%s'\n",
+ yyextra->type.data(),yyextra->className.data(),classTNames.data(),
+ yyextra->name.data(),funcTNames.data(),yyextra->args.data()
);
}
@@ -347,11 +359,11 @@ int main()
dumpDecl("const A<T>::Value* A<T>::getValue<S>(const A<T>&a)");
dumpDecl("func()");
dumpDecl("friend void bla<>()");
- dumpDecl("name< T > :: operator () (int bla)");
- dumpDecl("name< T > :: operator << (int bla)");
- dumpDecl("name< T > :: operator << <> (int bla)");
- dumpDecl("className::func()");
- dumpDecl("void ( * Name < T > :: bla ) ( int, char * )");
+ dumpDecl("yyextra->name< T > :: operator () (int bla)");
+ dumpDecl("yyextra->name< T > :: operator << (int bla)");
+ dumpDecl("yyextra->name< T > :: operator << <> (int bla)");
+ dumpDecl("yyextra->className::func()");
+ dumpDecl("void ( * yyextra->Name < T > :: bla ) ( int, char * )");
}
#endif