Doxygen
Loading...
Searching...
No Matches
scanner.l
Go to the documentation of this file.
1/*****************************************************************************
2 *
3 * Copyright (C) 1997-2021 by Dimitri van Heesch.
4 *
5 * Permission to use, copy, modify, and distribute this software and its
6 * documentation under the terms of the GNU General Public License is hereby
7 * granted. No representations are made about the suitability of this software
8 * for any purpose. It is provided "as is" without express or implied warranty.
9 * See the GNU General Public License for more details.
10 *
11 * Documents produced by Doxygen are derivative works derived from the
12 * input used in their production; they are not affected by this license.
13 *
14 */
15%option never-interactive
16%option prefix="scannerYY"
17%option reentrant
18%option extra-type="struct scannerYY_state *"
19%top{
20#include <stdint.h>
21// forward declare yyscan_t to improve typesafety
22#define YY_TYPEDEF_YY_SCANNER_T
23struct yyguts_t;
24typedef yyguts_t *yyscan_t;
yyguts_t * yyscan_t
Definition code.l:24
25}
26
27%{
28
29// own header
30#include "scanner.h"
31
32// standard includes
33#include <algorithm>
34#include <cstdint>
35#include <memory>
36#include <utility>
37#include <vector>
38
39// other includes
40#include "arguments.h"
41#include "clangparser.h"
42#include "commentscan.h"
43#include "config.h"
44#include "debug.h"
45#include "defargs.h"
46#include "doxygen.h"
47#include "entry.h"
48#include "filedef.h"
49#include "filename.h"
50#include "markdown.h"
51#include "md5hash.h"
52#include "message.h"
53#include "moduledef.h"
54#include "regex.h"
55#include "stringutil.h"
56#include "trace.h"
57#include "util.h"
58
59#define YY_NO_INPUT 1
60#define YY_NO_UNISTD_H 1
61
63{
66 const char * inputString = nullptr;
68 int lastContext = 0;
69 int lastCContext = 0;
94 Protection protection = Protection::Public;
95 Protection baseProt = Protection::Public;
96 bool exported = false;
97 int sharpCount = 0 ;
98 int roundCount = 0 ;
99 int curlyCount = 0 ;
101 int squareCount = 0 ;
102 int padCount = 0 ;
103 std::shared_ptr<Entry> current;
104 std::shared_ptr<Entry> current_root;
105 std::shared_ptr<Entry> previous;
106 std::shared_ptr<Entry> tempEntry;
107 std::shared_ptr<Entry> firstTypedefEntry;
108 std::shared_ptr<Entry> memspecEntry;
109 int yyLineNr = 1 ;
110 int yyBegLineNr = 1 ;
111 size_t yyColNr = 1 ;
112 size_t yyBegColNr = 1 ;
114 MethodTypes mtype = MethodTypes::Method;
115 bool isStatic = false;
116 Specifier virt = Specifier::Normal;
117 Specifier baseVirt = Specifier::Normal;
121 bool isTypedef = false;
126 DString* specName = nullptr;
127
128 SrcLangExt language = SrcLangExt::Unknown;
129 bool insideIDL = false; //!< processing IDL code?
130 bool insideJava = false; //!< processing Java code?
131 bool insideCS = false; //!< processing C# code?
132 bool insideD = false; //!< processing D code?
133 bool insidePHP = false; //!< processing PHP code?
134 bool insideObjC = false; //!< processing Objective C code?
135 bool insideCli = false; //!< processing C++/CLI code?
136 bool insideJS = false; //!< processing JavaScript code?
137 bool insideSlice = false; //!< processing Slice code?
138 bool insideCpp = true; //!< processing C/C++ code
140
141 bool insideCppQuote = false;
142 bool insideProtocolList = false;
143 bool doxygenComment = false;
144
155
157 char lastCopyArgChar = '\0';
158
174
175 bool insideFormula = false;
176 bool insideTryBlock = false;
177 bool insideCode = false;
178 bool needsSemi = false;
179
181
185
189 bool isCodeBlock = false;
190 bool docBlockInBody = false;
191 bool docBlockAutoBrief = false;
192 char docBlockTerm = '\0';
193
196 bool odlProp = false;
197
198 bool externLinkage = false;
199
201
202 int column = 0;
203
204 size_t fencedSize = 0;
206 using EntryRelation = std::pair< Entry*, std::shared_ptr<Entry> >;
207 using EntryRelations = std::vector<EntryRelation>;
210
212
213 bool usingNewVarNeeded = false;
214
215 int fakeNS = 0; //<! number of file scoped namespaces in CSharp file
217
218 int anonCount = 0;
219 int anonNSCount = 0;
220
221 bool keepComment = false;
222};
223
224[[maybe_unused]] static const char *stateToString(int state);
225//-----------------------------------------------------------------------------
226
227// forward declarations for stateless functions
228static inline size_t computeIndent(const char *s,size_t startIndent);
229static inline void initMethodProtection(yyscan_t yyscanner,Protection prot);
230static DString stripQuotes(const char *s);
231static DString stripFuncPtr(const DString &type);
232static bool nameIsOperator(DString &name);
234static bool startOfRequiresExpression(const DString &req);
235
236// forward declarations for stateful functions
237static void initParser(yyscan_t yyscanner);
238static void initEntry(yyscan_t yyscanner);
239static void lineCount(yyscan_t yyscanner);
240static void addType(yyscan_t yyscanner);
241static void setContext(yyscan_t yyscanner);
242static void prependScope(yyscan_t yyscanner);
243static void startCommentBlock(yyscan_t yyscanner,bool);
244static void handleCommentBlock(yyscan_t yyscanner,const DString &doc,bool brief);
245static void handleParametersCommentBlocks(yyscan_t yyscanner,ArgumentList &al);
246static bool checkForKnRstyleC(yyscan_t yyscanner);
247static void splitKnRArg(yyscan_t yyscanner,DString &oldStyleArgPtr,DString &oldStyleArgName);
248static void addKnRArgInfo(yyscan_t yyscanner,const DString &type,const DString &name,
249 const DString &brief,const DString &docs);
250static int yyread(yyscan_t yyscanner,char *buf,int max_size);
251static void setJavaProtection(yyscan_t yyscanner);
252static void storeClangId(yyscan_t yyscanner,const char *id);
253static void startVerbatimBlock(yyscan_t yyscanner,const DString &blockName,size_t fencedSize=0,bool codeBlock=false);
254static bool endVerbatimBlock(yyscan_t yyscanner,const DString &blockName,size_t fencedSize=0);
255static DString generateAnonymousAnchor(const DString &fileName,int count);
256
257
258/* ----------------------------------------------------------------- */
259#undef YY_INPUT
260#define YY_INPUT(buf,result,max_size) result=yyread(yyscanner,buf,max_size);
261
262// otherwise the filename would be the name of the converted file (*.cpp instead of *.l)
263static inline const char *getLexerFILE() {return __FILE__;}
264#include "doxygen_lex.h"
265
This class represents an function or template argument list.
Definition arguments.h:66
Clang parser object for a single translation unit, which consists of a source file and the directly o...
Definition clangparser.h:25
A String class for use with Doxygen wrapping std::string and adding some additional functionality off...
Definition dstring.h:88
Abstract interface for outline parsers.
Definition parserintf.h:41
Text streaming class that buffers data.
Definition textstream.h:36
Interface for the comment block scanner.
#define lineCount(s, len)
static DString generateAnonymousAnchor(const DString &fileName, int count)
Definition scanner.l:8113
static void startVerbatimBlock(yyscan_t yyscanner, const DString &blockName, size_t fencedSize=0, bool codeBlock=false)
Definition scanner.l:8241
static void storeClangId(yyscan_t yyscanner, const char *id)
Definition scanner.l:8132
static bool endVerbatimBlock(yyscan_t yyscanner, const DString &blockName, size_t fencedSize=0)
Definition scanner.l:8255
static void startCommentBlock(yyscan_t yyscanner, bool)
Definition scanner.l:8496
static void setContext(yyscan_t yyscanner)
Definition scanner.l:8293
static bool startOfRequiresExpression(const DString &req)
Definition scanner.l:8274
static void initParser(yyscan_t yyscanner)
Definition scanner.l:8068
static DString stripFuncPtr(const DString &type)
Definition scanner.l:8228
static bool checkForKnRstyleC(yyscan_t yyscanner)
Definition scanner.l:8333
static void addKnRArgInfo(yyscan_t yyscanner, const DString &type, const DString &name, const DString &brief, const DString &docs)
Definition scanner.l:8453
static int yyread(yyscan_t yyscanner, char *buf, int max_size)
Definition scanner.l:8054
static void initMethodProtection(yyscan_t yyscanner, Protection prot)
Definition scanner.l:8183
static const char * stateToString(int state)
void fixArgumentListForJavaScript(ArgumentList &al)
Definition scanner.l:8482
static void splitKnRArg(yyscan_t yyscanner, DString &oldStyleArgPtr, DString &oldStyleArgName)
Definition scanner.l:8364
static bool nameIsOperator(DString &name)
Definition scanner.l:8282
static void handleParametersCommentBlocks(yyscan_t yyscanner, ArgumentList &al)
Definition scanner.l:8593
static void prependScope(yyscan_t yyscanner)
Definition scanner.l:8315
static const char * getLexerFILE()
Definition scanner.l:263
static void setJavaProtection(yyscan_t yyscanner)
Definition scanner.l:8347
static void addType(yyscan_t yyscanner)
Definition scanner.l:8195
static DString stripQuotes(const char *s)
Definition scanner.l:8216
static size_t computeIndent(const char *s, size_t startIndent)
Definition scanner.l:8168
static void handleCommentBlock(yyscan_t yyscanner, const DString &doc, bool brief)
Definition scanner.l:8533
static void initEntry(yyscan_t yyscanner)
Definition scanner.l:8092
Some helper functions for std::string.
DString templateStr
Definition scanner.l:123
DString idlProp
Definition scanner.l:195
TextStream * pSkipInterpString
Definition scanner.l:172
EntryRelations outerScopeEntries
Definition scanner.l:208
bool docBlockAutoBrief
Definition scanner.l:191
int lastCopyArgStringContext
Definition scanner.l:149
Specifier baseVirt
Definition scanner.l:117
std::shared_ptr< Entry > firstTypedefEntry
Definition scanner.l:107
int lastDeprecatedContext
Definition scanner.l:75
DString aliasName
Definition scanner.l:124
TextStream docBlock
Definition scanner.l:187
bool insideJS
processing JavaScript code?
Definition scanner.l:136
bool insideProtocolList
Definition scanner.l:142
DString * copyArgString
Definition scanner.l:152
OutlineParserInterface * thisParser
Definition scanner.l:64
int lastDocContext
Definition scanner.l:70
DString fileName
Definition scanner.l:113
std::shared_ptr< Entry > tempEntry
Definition scanner.l:106
int lastStringContext
Definition scanner.l:74
std::shared_ptr< Entry > memspecEntry
Definition scanner.l:108
TextStream * pCopySquareGString
Definition scanner.l:167
int lastInitializerContext
Definition scanner.l:80
bool doxygenComment
Definition scanner.l:143
std::shared_ptr< Entry > previous
Definition scanner.l:105
int lastPreLineCtrlContext
Definition scanner.l:82
DString baseName
Definition scanner.l:125
int lastDefineContext
Definition scanner.l:90
MethodTypes mtype
Definition scanner.l:114
ClangTUParser * clangParser
Definition scanner.l:211
int lastSquareContext
Definition scanner.l:79
int lastAlignAsContext
Definition scanner.l:91
bool insideCS
processing C# code?
Definition scanner.l:131
ArgumentList * currentArgumentList
Definition scanner.l:156
DString * pCopyC11AttributeString
Definition scanner.l:164
TextStream * pCopyCurlyGString
Definition scanner.l:165
size_t yyBegColNr
Definition scanner.l:112
int lastCommentInArgContext
Definition scanner.l:86
int lastHereDocContext
Definition scanner.l:89
int lastSharpContext
Definition scanner.l:78
DString * pCopyRoundString
Definition scanner.l:160
int lastRoundContext
Definition scanner.l:77
DString msType
Definition scanner.l:118
Specifier virt
Definition scanner.l:116
DString briefBackup
Definition scanner.l:184
int lastSkipInterpVerbStringContext
Definition scanner.l:85
bool stopAtInvalidString
Definition scanner.l:139
DString * pCopyRawString
Definition scanner.l:163
bool insideCppQuote
Definition scanner.l:141
DString delimiter
Definition scanner.l:200
bool externLinkage
Definition scanner.l:198
const char * inputString
Definition scanner.l:66
DString docBackup
Definition scanner.l:183
DString programStr
Definition scanner.l:209
TextStream * pSkipVerbString
Definition scanner.l:171
std::pair< Entry *, std::shared_ptr< Entry > > EntryRelation
Definition scanner.l:206
SrcLangExt language
Definition scanner.l:128
int lastC11AttributeContext
Definition scanner.l:92
Protection baseProt
Definition scanner.l:95
DString * pCopyCurlyString
Definition scanner.l:161
bool insidePHP
processing PHP code?
Definition scanner.l:133
std::shared_ptr< Entry > current_root
Definition scanner.l:104
int lastCSConstraint
Definition scanner.l:88
int lastCurlyContext
Definition scanner.l:76
CommentScanner commentScanner
Definition scanner.l:65
DString funcPtrType
Definition scanner.l:122
int lastModifierContext
Definition scanner.l:93
DString idlAttr
Definition scanner.l:194
bool insideIDL
processing IDL code?
Definition scanner.l:129
bool insideTryBlock
Definition scanner.l:176
Protection protection
Definition scanner.l:94
bool insideSlice
processing Slice code?
Definition scanner.l:137
int lastCPPContext
Definition scanner.l:71
DString oldStyleArgType
Definition scanner.l:182
DString msName
Definition scanner.l:119
TextStream * pCopyHereDocGString
Definition scanner.l:169
bool insideObjC
processing Objective C code?
Definition scanner.l:134
int lastSkipSharpContext
Definition scanner.l:72
bool insideCli
processing C++/CLI code?
Definition scanner.l:135
int currentArgumentContext
Definition scanner.l:148
DString * pCopySharpString
Definition scanner.l:162
int initBracketCount
Definition scanner.l:180
size_t yyColNr
Definition scanner.l:111
DString * pCopyQuotedString
Definition scanner.l:159
int requiresContext
Definition scanner.l:151
int lastSkipVerbStringContext
Definition scanner.l:83
TextStream * pCopyRawGString
Definition scanner.l:170
DString docBlockName
Definition scanner.l:188
bool docBlockInBody
Definition scanner.l:190
int lastCopyArgContext
Definition scanner.l:150
int inputPosition
Definition scanner.l:67
TextStream * pCopyQuotedGString
Definition scanner.l:168
DString msArgs
Definition scanner.l:120
TextStream * pSkipInterpVerbString
Definition scanner.l:173
std::shared_ptr< Entry > current
Definition scanner.l:103
char lastCopyArgChar
Definition scanner.l:157
DString dummyRawString
Definition scanner.l:154
int lastSkipInterpStringContext
Definition scanner.l:84
bool insideD
processing D code?
Definition scanner.l:132
char docBlockTerm
Definition scanner.l:192
size_t fencedSize
Definition scanner.l:204
std::vector< EntryRelation > EntryRelations
Definition scanner.l:207
TextStream * pCopyRoundGString
Definition scanner.l:166
bool insideCpp
processing C/C++ code
Definition scanner.l:138
int docBlockContext
Definition scanner.l:186
TextStream dummyTextStream
Definition scanner.l:216
int lastClassTemplSpecContext
Definition scanner.l:81
bool insideFormula
Definition scanner.l:175
bool usingNewVarNeeded
Definition scanner.l:213
DString * specName
Definition scanner.l:126
DString fullArgString
Definition scanner.l:153
int lastSkipRoundContext
Definition scanner.l:73
bool insideJava
processing Java code?
Definition scanner.l:130
int lastRawStringContext
Definition scanner.l:87
MethodTypes
Definition types.h:119
Protection
Definition types.h:32
SrcLangExt
Definition types.h:207
Specifier
Definition types.h:80
A bunch of utility functions.
266%}
267
268 /* start command character */
269CMD ("\\"|"@")
270BN [ \t\n\r]
271BNopt {BN}*
272BL [ \t\r]*"\n"
273B [ \t]
274Bopt {B}*
275NOTopt (("!"{BNopt})|("not"{BN}+))?
276DIGIT [0-9]
277HEXDIGIT ({DIGIT}|[a-f]|[A-F])
278ID [$a-z_A-Z\x80-\xFF][$a-z_A-Z0-9\x80-\xFF]*
279SCOPENAME "$"?(({ID}?{BN}*"::"{BN}*)*)(((~|!){BN}*)?{ID})
280TSCOPE {ID}("<"[a-z_A-Z0-9 \t\*\&,:]*">")?
281CSSCOPENAME (({ID}?{BN}*"."{BN}*)*)((~{BN}*)?{ID})
282PRE [pP][rR][eE]
283CODE [cC][oO][dD][eE]
284CHARLIT (("'"\\x[0-9a-fA-F]{1,2}"'")|("'"\\‍[0-7]{1,3}"'")|("'"\\."'")|("'"[^'\\\n]{1,4}"'"))
285PHPKW ("require"|"require_once"|"include"|"include_once"|"echo")[^a-zA-Z0-9_;]
286PHPUSEKW ("public"|"private"|"protected")
287IDLATTR ("["[^\‍]]*"]"){BN}*
288TYPEDEFPREFIX (("typedef"{BN}+)?)((("volatile"|"const"){BN}+)?)
289RAWBEGIN (u|U|L|u8)?R\"[^ \t\‍(\‍)\\‍]{0,16}"("
290RAWEND ")"[^ \t\‍(\‍)\\‍]{0,16}\"
291ARITHOP "+"|"-"|"/"|"*"|"%"|"--"|"++"
292ASSIGNOP "="|"*="|"/="|"%="|"+="|"-="|"<<="|">>="|"&="|"^="|"|="
293LOGICOP "=="|"!="|">"|"<"|">="|"<="|"&&"|"||"|"!"|"<=>"
294BITOP "&"|"|"|"^"|"<<"|">>"|"~"
295OPERATOR "operator"{B}*({ARITHOP}|{ASSIGNOP}|{LOGICOP}|{BITOP})
296FUNCOP "operator"("()"|"[]"|{B}+[^;\n]+)
297MODULE_ID ({ID}".")*{ID}
298LINENR {B}*[1-9][0-9]*
299FILEICHAR [a-z_A-Z0-9\x80-\xFF\\:\\\/\-\+=&#@~]
300FILEECHAR [a-z_A-Z0-9\x80-\xFF\-\+=&#@~]
301FILECHARS {FILEICHAR}*{FILEECHAR}+
302HFILEMASK {FILEICHAR}*("."{FILEICHAR}+)+{FILECHARS}*
303VFILEMASK {FILECHARS}("."{FILECHARS})*
304FILEMASK {VFILEMASK}|{HFILEMASK}
305
306 /* no comment start / end signs inside square brackets */
307NCOMM [^/\*]
308 // C start comment
309CCS "/\*"
310 // C end comment
311CCE "*\/"
312 // Cpp comment
313CPPC "/\/"
314 // doxygen C start comment
315DCOMMC ("/\*!"|"/\**")
316 // doxygen Cpp start comment
317DCOMMCPP ("/\/!"|"/\/\/")
318 // doxygen start comment
319DCOMM {DCOMMC}|{DCOMMCPP}
320
321 // Optional any character
322ANYopt .*
323 // Optional all but newline
324NONLopt [^\n]*
325
326%option noyywrap
327
328 /* language parsing states */
329
330%x AlignAs
331%x AlignAsEnd
332%x SDefine
333%x DefineEnd
334%x CompoundName
335%x ClassVar
336%x CSConstraintName
337%x CSConstraintType
338%x CSIndexer
339%x ClassCategory
340%x ClassTemplSpec
341%x CliPropertyType
342%x CliPropertyIndex
343%x CliOverride
344%x Bases
345%x BasesProt
346%x NextSemi
347%x BitFields
348%x EnumBaseType
349%x FindMembers
350%x FindMembersPHP
351%x FindMemberName
352%x FindFields
353%x FindConceptParts
354%x FindConceptDocs
355%x FindConceptCxxDocs
356%x SFunction
357%x FuncRound
358%x ExcpRound
359%x ExcpList
360%x FuncQual
361%x TrailingReturn
362%x Operator
363%x Array
364%x ReadBody
365%x ReadNSBody
366%x ReadBodyIntf
367%x ReadExpressionBody
368%x Using
369%x UsingAlias
370%x UsingDirective
371%x SkipCurly
372%x SkipCurlyCpp
373%x SkipCurlyEndDoc
374%x SkipString
375%x SkipPHPString
376%x SkipInits
377%x SkipC11Inits
378%x SkipCPP
379%x SkipComment
380%x SkipCxxComment
381%x SkipCurlyBlock
382%x SkipRoundBlock
383%x Sharp
384%x SkipRound
385%x SkipSquare
386%x StaticAssert
387%x DeclType
388%x TypedefName
389%x TryFunctionBlock
390%x TryFunctionBlockEnd
391%x Comment
392%x PackageName
393%x JavaImport
394%x IDLImport
395%x PHPUse
396%x PHPUseAs
397%x CSAccessorDecl
398%x CSGeneric
399%x PreLineCtrl
400%x DefinePHP
401%x DefinePHPEnd
402%x OldStyleArgs
403%x SkipVerbString
404%x SkipInterpString
405%x SkipInterpVerbString
406%x ObjCMethod
407%x ObjCReturnType
408%x ObjCParams
409%x ObjCParamType
410%x ObjCProtocolList
411%x ObjCPropAttr
412%x ObjCSkipStatement
413%x QtPropType
414%x QtPropAttr
415%x QtPropRead
416%x QtPropWrite
417%x ReadInitializer
418%x ReadInitializerPtr
419%x InitCopyComment
420%x UNOIDLAttributeBlock
421%x GetCallType
422%x CppQuote
423%x EndCppQuote
424%x MemberSpec
425%x MemberSpecSkip
426%x EndTemplate
427%x FuncPtr
428%x FuncPtrOperator
429%x EndFuncPtr
430%x ReadFuncArgType
431%x ReadTempArgs
432%x IDLUnionCase
433%x NSAliasName
434%x NSAliasArg
435%x CopyString
436%x CopyPHPString
437%x CopyGString
438%x CopyPHPGString
439%x CopyRound
440%x CopySharp
441%x CopyCurly
442%x CopyC11Attribute
443%x CopyComment
444%x GCopyRound
445%x GCopySquare
446%x GCopyCurly
447%x GCopyComment
448%x SkipUnionSwitch
449%x Specialization
450%x SpecializationSingleQuote
451%x SpecializationDoubleQuote
452%x FuncFunc
453%x FuncFuncEnd
454%x FuncFuncType
455%x FuncFuncArray
456%x CopyArgString
457%x CopyArgPHPString
458%x CopyArgRound
459%x CopyArgSquare
460%x CopyArgSharp
461%x CopyArgComment
462%x CopyArgCommentLine
463%x CopyArgVerbatim
464%x HereDoc
465%x HereDocEnd
466%x CopyHereDoc
467%x CopyHereDocEnd
468%x RawString
469%x RawGString
470%x CSString
471%x CppProt
472
473%x IDLAttribute
474%x IDLProp
475%x IDLPropName
476
477 /** Slice states */
478
479%x SliceOptional
480%x SliceMetadata
481%x SliceSequence
482%x SliceSequenceName
483%x SliceDictionary
484%x SliceDictionaryName
485
486 /** Prototype scanner states */
487
488%x Prototype
489%x PrototypePtr
490%x PrototypeQual
491%x PrototypeExc
492%x PrototypeSkipLine
493
494 /** comment parsing states */
495
496%x DocLine
497%x DocBlock
498%x DocCopyBlock
499
500 /** C++20 concepts */
501
502%x RequiresClause
503%x RequiresExpression
504%x ConceptName
505
506 /** Object-C Deprecated */
507%x Deprecated_round
508
509
510 /** C++20 modules */
511%x ModuleName
512%x ModuleImport
514
515<*>"DEPRECATED_ATTRIBUTE" { // Object-C attribute
516 if (!yyextra->insideObjC) REJECT;
517 }
518<*>"DEPRECATED_MSG_ATTRIBUTE(\"" { // Object-C attribute
519 if (!yyextra->insideObjC) REJECT;
520 yyextra->lastDeprecatedContext=YY_START;
521 yyextra->lastStringContext=Deprecated_round;
522 BEGIN(SkipString);
523 }
524<Deprecated_round>")" {
525 BEGIN(yyextra->lastDeprecatedContext);
526 }
527<Deprecated_round>{BNopt} {
528 lineCount(yyscanner);
529 }
530<Deprecated_round>. { }
531<NextSemi>"{" {
532 yyextra->curlyCount=0;
533 yyextra->needsSemi = true;
534 BEGIN(SkipCurlyBlock);
535 }
536<NextSemi>"(" {
537 yyextra->roundCount=0;
538 BEGIN(SkipRoundBlock);
539 }
540<SkipRoundBlock>"(" {
541 ++yyextra->roundCount;
542 }
543<SkipRoundBlock>")" {
544 if (yyextra->roundCount )
545 --yyextra->roundCount ;
546 else
547 BEGIN( NextSemi ) ;
548 }
549<SkipCurlyBlock>"{" {
550 ++yyextra->curlyCount ;
551 }
552<SkipCurlyBlock>"}" {
553 if( yyextra->curlyCount )
554 {
555 --yyextra->curlyCount ;
556 }
557 else if (yyextra->needsSemi)
558 {
559 BEGIN( NextSemi );
560 }
561 else
562 {
563 BEGIN( FindMembers );
564 }
565 }
566<NextSemi>\' {
567 if (yyextra->insidePHP)
568 {
569 yyextra->lastStringContext=NextSemi;
570 BEGIN(SkipPHPString);
571 }
572 }
573<NextSemi>{CHARLIT} { if (yyextra->insidePHP) REJECT; }
574<NextSemi>\" {
575 yyextra->lastStringContext=NextSemi;
576 BEGIN(SkipString);
577 }
578<NextSemi>[;,] {
579 unput(*yytext);
580 BEGIN( FindMembers );
581 }
582<BitFields>[;,] {
583 unput(*yytext);
584 BEGIN( FindMembers );
585 }
586<EnumBaseType>[{;,] {
587 yyextra->current->args = yyextra->current->args.simplifyWhiteSpace();
588 unput(*yytext);
589 BEGIN( ClassVar );
590 }
591<FindMembers>"<?php" { // PHP code with unsupported extension?
592 yyextra->insidePHP = true;
593 }
594<FindMembersPHP>"<?"("php"?) { // PHP code start
595 BEGIN( FindMembers );
596 }
597<FindMembersPHP>"<script"{BN}+"language"{BN}*"="{BN}*['"]?"php"['"]?{BN}*">" { // PHP code start
598 lineCount(yyscanner) ;
599 BEGIN( FindMembers );
600 }
601<FindMembers>"?>"|"</script>" { // PHP code end
602 if (yyextra->insidePHP)
603 BEGIN( FindMembersPHP );
604 else
605 REJECT;
606 }
607<FindMembersPHP>[^\n<]+ { // Non-PHP code text, ignore
608 }
609<FindMembersPHP>\n { // Non-PHP code text, ignore
610 lineCount(yyscanner);
611 }
612<FindMembersPHP>. { // Non-PHP code text, ignore
613 }
614<FindMembers>{PHPKW} { if (yyextra->insidePHP)
615 BEGIN( NextSemi );
616 else
617 REJECT;
618 }
619<FindMembers>"%{"[^\n]* { // Mozilla XPIDL lang-specific block
620 if (!yyextra->insideIDL)
621 REJECT;
622 }
623<FindMembers>"%}" { // Mozilla XPIDL lang-specific block end
624 if (!yyextra->insideIDL)
625 REJECT;
626 }
627<FindMembers>{B}*("properties"){BN}*":"{BN}* { // IDL or Borland C++ builder property
628 initMethodProtection(yyscanner,Protection::Public);
629 yyextra->current->mtype = yyextra->mtype = MethodTypes::Property;
630 }
631
632<FindMembers>{B}*"k_dcop"{BN}*":"{BN}* {
633 initMethodProtection(yyscanner,Protection::Public);
634 yyextra->current->mtype = yyextra->mtype = MethodTypes::DCOP;
635 }
636
637<FindMembers>{B}*("signals"|"Q_SIGNALS"){BN}*":"{BN}* {
638 initMethodProtection(yyscanner,Protection::Public);
639 yyextra->current->mtype = yyextra->mtype = MethodTypes::Signal;
640 }
641
642<FindMembers>{B}*"public"{BN}*("slots"|"Q_SLOTS"){BN}*":"{BN}* {
643 initMethodProtection(yyscanner,Protection::Public);
644 yyextra->current->mtype = yyextra->mtype = MethodTypes::Slot;
645 }
646
647<FindMembers>{B}*"protected"{BN}*("slots"|"Q_SLOTS"){BN}*":"{BN}* {
648 initMethodProtection(yyscanner,Protection::Protected);
649 yyextra->current->mtype = yyextra->mtype = MethodTypes::Slot;
650 }
651
652<FindMembers>{B}*"private"{BN}*("slots"|"Q_SLOTS"){BN}*":"{BN}* {
653 initMethodProtection(yyscanner,Protection::Private);
654 yyextra->current->mtype = yyextra->mtype = MethodTypes::Slot;
655 }
656<FindMembers>{B}*("public"|"methods"|"__published"){BN}*":"{BN}* {
657 initMethodProtection(yyscanner,Protection::Public);
658 }
659<FindMembers>{B}*"internal"{BN}*":"{BN}* { // for now treat C++/CLI's internal as package...
660 if (yyextra->insideCli)
661 {
662 initMethodProtection(yyscanner,Protection::Package);
663 }
664 else
665 {
666 REJECT;
667 }
668 }
669<FindMembers>{B}*"protected"{BN}*":"{BN}* {
670 initMethodProtection(yyscanner,Protection::Protected);
671 }
672<FindMembers>{B}*"private"{BN}*":"{BN}* {
673 initMethodProtection(yyscanner,Protection::Private);
674 }
675<FindMembers>{B}*"public"/({BN}|{CCS}|{CPPC}) {
676 if (!yyextra->insideCpp) REJECT;
677 initMethodProtection(yyscanner,Protection::Public);
678 BEGIN(CppProt);
679 }
680<FindMembers>{B}*"protected"/({BN}|{CCS}|{CPPC}) {
681 if (!yyextra->insideCpp) REJECT;
682 initMethodProtection(yyscanner,Protection::Protected);
683 BEGIN(CppProt);
684 }
685<FindMembers>{B}*"private"/({BN}|{CCS}|{CPPC}) {
686 if (!yyextra->insideCpp) REJECT;
687 initMethodProtection(yyscanner,Protection::Private);
688 BEGIN(CppProt);
689 }
690<CppProt>":" {
691 BEGIN(FindMembers);
692 }
693<CppProt>. {
694 unput(*yytext);
695 BEGIN(FindMembers);
696 }
697<CppProt>{BN}+ { lineCount(yyscanner); }
698<CppProt>{CPPC}.*\n { lineCount(yyscanner); }
699<CppProt>{CCS} { yyextra->lastCContext = YY_START ;
700 BEGIN( SkipComment ) ;
701 }
702<CppProt>("slots"|"Q_SLOTS") {
703 yyextra->current->mtype = yyextra->mtype = MethodTypes::Slot;
704 }
705<FindMembers>{B}*"event"{BN}+ {
706 if (yyextra->insideCli)
707 {
708 // C++/CLI event
709 lineCount(yyscanner) ;
710 yyextra->current->mtype = yyextra->mtype = MethodTypes::Event;
711 yyextra->current->bodyLine = yyextra->yyLineNr;
712 yyextra->current->bodyColumn = yyextra->yyColNr;
713 yyextra->curlyCount=0;
714 BEGIN( CliPropertyType );
715 }
716 else if (yyextra->insideCS)
717 {
718 lineCount(yyscanner) ;
719 yyextra->current->mtype = MethodTypes::Event;
720 yyextra->current->bodyLine = yyextra->yyLineNr;
721 yyextra->current->bodyColumn = yyextra->yyColNr;
722 }
723 else
724 {
725 REJECT;
726 }
727 }
728<FindMembers>{B}*"property"{BN}+ {
729 if (yyextra->insideCli)
730 {
731 // C++/CLI property
732 lineCount(yyscanner) ;
733 yyextra->current->mtype = yyextra->mtype = MethodTypes::Property;
734 yyextra->current->bodyLine = yyextra->yyLineNr;
735 yyextra->current->bodyColumn = yyextra->yyColNr;
736 yyextra->curlyCount=0;
737 BEGIN( CliPropertyType );
738 }
739 else
740 {
741 REJECT;
742 }
743 }
744<CliPropertyType>{ID} {
745 addType(yyscanner);
746 yyextra->current->name = yytext;
747 }
748<CliPropertyType>"[" { // C++/CLI indexed property
749 yyextra->current->args = "[";
750 BEGIN( CliPropertyIndex );
751 }
752<CliPropertyType>"{" {
753 yyextra->curlyCount=0;
754 //printf("event: '%s' '%s'\n",qPrint(yyextra->current->type),qPrint(yyextra->current->name));
755 BEGIN( CSAccessorDecl );
756 }
757<CliPropertyType>";" {
758 unput(*yytext);
759 BEGIN( FindMembers );
760 }
761<CliPropertyType>\n {
762 lineCount(yyscanner);
763 }
764<CliPropertyType>{B}* {
765 }
766<CliPropertyType>. {
767 addType(yyscanner);
768 yyextra->current->type += yytext;
769 }
770<CliPropertyIndex>"]" {
771 BEGIN( CliPropertyType );
772 yyextra->current->args+=yytext;
773 }
774<CliPropertyIndex>. {
775 yyextra->current->args+=yytext;
776 }
777 /*
778<FindMembers>{B}*"property"{BN}+ {
779 if (!yyextra->current->type.empty())
780 {
781 REJECT;
782 }
783 else
784 {
785 yyextra->current->mtype = yyextra->mtype = MethodTypes::Property;
786 lineCount(yyscanner);
787 }
788 }
789 */
790<FindMembers>{B}*"@private"{BN}+ {
791 initMethodProtection(yyscanner,Protection::Private);
792 }
793<FindMembers>{B}*"@protected"{BN}+ {
794 initMethodProtection(yyscanner,Protection::Protected);
795 }
796<FindMembers>{B}*"@public"{BN}+ {
797 initMethodProtection(yyscanner,Protection::Public);
798 }
799<FindMembers>[\-+]{BN}* {
800 if (!yyextra->insideObjC)
801 {
802 REJECT;
803 }
804 else
805 {
806 yyextra->current->fileName = yyextra->fileName;
807 yyextra->current->startLine = yyextra->yyLineNr;
808 yyextra->current->startColumn = yyextra->yyColNr;
809 yyextra->current->bodyLine = yyextra->yyLineNr;
810 yyextra->current->bodyColumn = yyextra->yyColNr;
811 yyextra->current->section = EntryType::makeFunction();
812 yyextra->language = yyextra->current->lang = SrcLangExt::ObjC;
813 yyextra->insideObjC = true;
814 yyextra->yyBegColNr = yyextra->yyColNr;
815 yyextra->yyBegLineNr = yyextra->yyLineNr;
816 yyextra->current->virt = Specifier::Virtual;
817
818 yyextra->current->isStatic=yytext[0]=='+';
819 initMethodProtection(yyscanner,Protection::Public);
820 BEGIN( ObjCMethod );
821 }
822 }
823<ObjCMethod>"(" { // start of method's return type
824 BEGIN( ObjCReturnType );
825 yyextra->current->type.clear();
826 yyextra->roundCount=0;
827 }
828<ObjCMethod>{ID} { // found method name
829 if (yyextra->current->type.empty())
830 {
831 yyextra->current->type += "id";
832 }
833 yyextra->current->name = yytext;
834 storeClangId(yyscanner,yytext);
835 }
836<ObjCMethod>":"{B}* { // start of parameter list
837 yyextra->current->name += ':';
838 Argument a;
839 yyextra->current->argList.push_back(a);
840 BEGIN( ObjCParams );
841 }
This class contains the information about the argument of a function or template.
Definition arguments.h:27
842<ObjCReturnType>[^()]* {
843 yyextra->current->type += yytext;
844 }
845<ObjCReturnType>"(^)(" { // Block return type
846 yyextra->current->type += yytext;
847 yyextra->roundCount++;
848 }
849<ObjCReturnType>"(" {
850 yyextra->current->type += yytext;
851 yyextra->roundCount++;
852 }
853<ObjCReturnType>")" {
854 if (yyextra->roundCount<=0)
855 {
856 BEGIN( ObjCMethod );
857 }
858 else
859 {
860 yyextra->current->type += yytext;
861 yyextra->roundCount--;
862 }
863 }
864<ObjCParams>({ID})?{BN}*":" { // Keyword of parameter
865 DString keyw = yytext;
866 keyw=keyw.left(keyw.length()-1).stripWhiteSpace(); // strip :
867 if (keyw.empty())
868 {
869 yyextra->current->name += " :";
870 }
871 else
872 {
873 yyextra->current->name += keyw+":";
874 }
875 if (yyextra->current->argList.back().type.empty())
876 {
877 yyextra->current->argList.back().type="id";
878 }
879 Argument a;
880 a.attrib=(DString)"["+keyw+"]";
881 yyextra->current->argList.push_back(a);
882 }
DString attrib
Definition arguments.h:42
void push_back(char c)
Definition dstring.h:206
bool empty() const
Returns true iff the string is empty (std::string compatible alias for isEmpty()).
Definition dstring.h:152
DString stripWhiteSpace() const
returns a copy of this string with leading and trailing whitespace removed
Definition dstring.h:341
DString left(size_t len) const
Definition dstring.h:310
size_t length() const
Returns the length of the string, not counting the 0-terminator.
Definition dstring.h:155
883<ObjCParams>{ID}{BN}* { // name of parameter
884 lineCount(yyscanner);
885 yyextra->current->argList.back().name=DString(yytext).stripWhiteSpace();
886 }
887<ObjCParams>","{BN}*"..." { // name of parameter
888 lineCount(yyscanner);
889 // do we want the comma as part of the name?
890 //yyextra->current->name += ",";
891 Argument a;
892 a.attrib="[,]";
893 a.type="...";
894 yyextra->current->argList.push_back(a);
895 }
DString type
Definition arguments.h:43
896 /*
897<ObjCParams>":" {
898 yyextra->current->name += ':';
899 }
900 */
901<ObjCParams>"(" {
902 yyextra->roundCount=0;
903 yyextra->current->argList.back().type.clear();
904 BEGIN( ObjCParamType );
905 }
906<ObjCParamType>"(" {
907 yyextra->roundCount++;
908 yyextra->current->argList.back().type+=yytext;
909 }
910<ObjCParamType>")"/{B}* {
911 if (yyextra->roundCount<=0)
912 {
913 BEGIN( ObjCParams );
914 }
915 else
916 {
917 yyextra->current->argList.back().type+=yytext;
918 yyextra->roundCount--;
919 }
920 }
921<ObjCParamType>[^()]* {
922 yyextra->current->argList.back().type+=DString(yytext).stripWhiteSpace();
923 }
924<ObjCMethod,ObjCParams>";" { // end of method declaration
925 if (!yyextra->current->argList.empty() && yyextra->current->argList.back().type.empty())
926 {
927 yyextra->current->argList.back().type="id";
928 }
929 if (yyextra->current->argList.empty()) // method without parameters
930 {
931 yyextra->current->argList.setNoParameters(true);
932 }
933 yyextra->current->args = argListToString(yyextra->current->argList);
934 //printf("argList=%s\n",qPrint(yyextra->current->args));
935 unput(';');
936 BEGIN( SFunction );
937 }
DString argListToString(const ArgumentList &al, bool useCanonicalType, bool showDefVals)
Definition util.cpp:860
938<ObjCMethod,ObjCParams>(";"{BN}+)?"{" { // start of a method body
939 lineCount(yyscanner);
940 //printf("Type=%s Name=%s args=%s\n",
941 // qPrint(yyextra->current->type),qPrint(yyextra->current->name),qPrint(argListToString(yyextra->current->argList))
942 // );
943 if (!yyextra->current->argList.empty() && yyextra->current->argList.back().type.empty())
944 {
945 yyextra->current->argList.back().type="id";
946 }
947 if (yyextra->current->argList.empty()) // method without parameters
948 {
949 yyextra->current->argList.setNoParameters(true);
950 }
951 yyextra->current->args = argListToString(yyextra->current->argList);
952 unput('{');
953 BEGIN( SFunction );
954 }
955<FindMembers>{B}*"sequence"{BN}*"<"{BN}* {
956 if (yyextra->insideSlice)
957 {
958 lineCount(yyscanner);
959 yyextra->current->bodyLine = yyextra->yyLineNr;
960 yyextra->current->bodyColumn = yyextra->yyColNr;
961 yyextra->current->fileName = yyextra->fileName ;
962 yyextra->current->startLine = yyextra->yyLineNr ;
963 yyextra->current->startColumn = yyextra->yyColNr;
964 yyextra->current->args.clear();
965 yyextra->current->section = EntryType::makeTypedef();
966 yyextra->isTypedef = true;
967 BEGIN( SliceSequence );
968 }
969 else
970 REJECT;
971 }
972<FindMembers>{B}*"dictionary"{BN}*"<"{BN}* {
973 if (yyextra->insideSlice)
974 {
975 lineCount(yyscanner);
976 yyextra->current->bodyLine = yyextra->yyLineNr;
977 yyextra->current->bodyColumn = yyextra->yyColNr;
978 yyextra->current->fileName = yyextra->fileName ;
979 yyextra->current->startLine = yyextra->yyLineNr ;
980 yyextra->current->startColumn = yyextra->yyColNr;
981 yyextra->current->args.clear();
982 yyextra->current->section = EntryType::makeTypedef() ;
983 yyextra->isTypedef = true;
984 BEGIN( SliceDictionary );
985 }
986 else
987 REJECT;
988 }
989<FindMembers>{BN}{1,80} {
990 lineCount(yyscanner);
991 }
992<FindMembers>"@"({ID}".")*{ID}{BN}*"(" {
993 if (yyextra->insideJava) // Java annotation
994 {
995 lineCount(yyscanner);
996 yyextra->lastSkipRoundContext = YY_START;
997 yyextra->roundCount=0;
998 BEGIN( SkipRound );
999 }
1000 else if (literal_at(yytext,"@property")) // ObjC 2.0 property
1001 {
1002 yyextra->current->mtype = yyextra->mtype = MethodTypes::Property;
1003 yyextra->current->spec.setReadable(true).setWritable(true).setAssign(true);
1004 yyextra->current->protection = Protection::Public ;
1005 unput('(');
1006 BEGIN( ObjCPropAttr );
1007 }
1008 else
1009 {
1010 REJECT;
1011 }
1012 }
bool literal_at(const char *data, const char(&str)[N])
returns true iff data points to a substring that matches string literal str
Definition stringutil.h:101
1013<ObjCPropAttr>"getter="{ID} {
1014 yyextra->current->read = yytext+7;
1015 }
1016<ObjCPropAttr>"setter="{ID} {
1017 yyextra->current->write = yytext+7;
1018 }
1019<ObjCPropAttr>"readonly" {
1020 yyextra->current->spec.setWritable(false);
1021 }
1022<ObjCPropAttr>"readwrite" { // default
1023 }
1024<ObjCPropAttr>"assign" { // default
1025 }
1026<ObjCPropAttr>"unsafe_unretained" {
1027 yyextra->current->spec.setAssign(false);
1028 yyextra->current->spec.setUnretained(true);
1029 }
1030<ObjCPropAttr>"retain" {
1031 yyextra->current->spec.setAssign(false);
1032 yyextra->current->spec.setRetain(true);
1033 }
1034<ObjCPropAttr>"copy" {
1035 yyextra->current->spec.setAssign(false);
1036 yyextra->current->spec.setCopy(true);
1037 }
1038<ObjCPropAttr>"weak" {
1039 yyextra->current->spec.setAssign(false);
1040 yyextra->current->spec.setWeak(true);
1041 }
1042<ObjCPropAttr>"strong" {
1043 yyextra->current->spec.setAssign(false);
1044 yyextra->current->spec.setStrong(true);
1045 }
1046<ObjCPropAttr>"nonatomic" {
1047 yyextra->current->spec.setNonAtomic(true);
1048 }
1049<ObjCPropAttr>")" {
1050 BEGIN(FindMembers);
1051 }
1052<FindMembers>"@"{ID}("."{ID})+ {
1053 if (yyextra->insideJava) // Java annotation
1054 {
1055 // skip annotation
1056 }
1057 else
1058 {
1059 REJECT;
1060 }
1061 }
1062<FindMembers>"@"{ID} {
1063 if (yyextra->insideJava) // Java annotation
1064 {
1065 // skip annotation
1066 }
1067 else if (dstrcmp(yytext,"@property")==0) // ObjC 2.0 property
1068 {
1069 yyextra->current->mtype = yyextra->mtype = MethodTypes::Property;
1070 yyextra->current->spec.setWritable(true).setReadable(true);
1071 yyextra->current->protection = Protection::Public ;
1072 }
1073 else if (dstrcmp(yytext,"@synthesize")==0)
1074 {
1075 BEGIN( ObjCSkipStatement );
1076 }
1077 else if (dstrcmp(yytext,"@dynamic")==0)
1078 {
1079 BEGIN( ObjCSkipStatement );
1080 }
1081 else
1082 {
1083 REJECT;
1084 }
1085 }
int dstrcmp(const char *str1, const char *str2)
Definition dstring.h:54
1086<ObjCSkipStatement>";" {
1087 BEGIN(FindMembers);
1088 }
1089<PackageName>{ID}(("."|"\\"){ID})* {
1090 yyextra->isTypedef=false;
1091 //printf("Found namespace %s lang=%d\n",yytext,yyextra->current->lang);
1092 yyextra->current->name = yytext;
1093 yyextra->current->name = substitute(yyextra->current->name,".","::");
1094 yyextra->current->name = substitute(yyextra->current->name,"\\","::");
1095 yyextra->current->section = EntryType::makeNamespace();
1096 yyextra->current->type = "namespace" ;
1097 yyextra->current->fileName = yyextra->fileName;
1098 yyextra->current->startLine = yyextra->yyLineNr;
1099 yyextra->current->startColumn = yyextra->yyColNr;
1100 yyextra->current->bodyLine = yyextra->yyLineNr;
1101 yyextra->current->bodyColumn = yyextra->yyColNr;
1102 lineCount(yyscanner);
1103 }
DString substitute(const DString &s, const DString &src, const DString &dst)
substitute all occurrences of src in s by dst
Definition dstring.cpp:485
1104<PackageName>";" {
1105 std::shared_ptr<Entry> tmp = yyextra->current;
1106 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
1107 yyextra->current_root = std::move(tmp);
1108 initEntry(yyscanner);
1109 BEGIN(FindMembers);
1110 }
static void initEntry(yyscan_t yyscanner)
1111<PackageName>"{" {
1112 yyextra->curlyCount=0;
1113 BEGIN( ReadNSBody );
1114 }
1115<FindMembers>{B}*"export"{BN}+"module"{BN}+ { // primary module interface unit
1116 if (!yyextra->insideCpp) REJECT;
1117 //printf("Interface module unit\n");
1118 yyextra->current->exported = true;
1119 lineCount(yyscanner);
1120 BEGIN( ModuleName );
1121 }
1122<FindMembers>{B}*"module"{BN}*";" { // global module section
1123 if (!yyextra->insideCpp) REJECT;
1124 if (!yyextra->current->type.empty() || !yyextra->current->name.empty()) REJECT;
1125 //printf("Implementation module unit\n");
1126 lineCount(yyscanner);
1127 BEGIN( FindMembers );
1128 }
1129<FindMembers>{B}*"module"{BN}+ { // module implementation unit
1130 if (!yyextra->insideCpp) REJECT;
1131 //printf("Implementation module unit\n");
1132 yyextra->current->exported = false;
1133 lineCount(yyscanner);
1134 BEGIN( ModuleName );
1135 }
1136<FindMembers>{B}*"export"{BN}+"import"{BN}+ { // export an imported module
1137 if (!yyextra->insideCpp) REJECT;
1138 yyextra->current->exported = true;
1139 lineCount(yyscanner);
1140 BEGIN( ModuleImport );
1141 }
1142<FindMembers>{B}*"import"{BN}+ { // start of a module import
1143 if (!yyextra->insideCpp) REJECT;
1144 lineCount(yyscanner);
1145 BEGIN( ModuleImport );
1146 }
1147<ModuleName>{MODULE_ID}{BN}*":"{BN}*{MODULE_ID} { // module partition name, e.g. A.B:C.D'
1148 DString name = yytext;
1149 size_t i = name.find(':');
1150 DString partition = name.mid(i+1).stripWhiteSpace();
1151 name = name.left(i).stripWhiteSpace();
1152 ModuleManager::instance().createModuleDef(yyextra->fileName,
1153 yyextra->yyLineNr,
1154 yyextra->yyColNr,
1155 yyextra->current->exported,
1156 name,
1157 partition);
1158 yyextra->current->section = EntryType::makeModuleDoc();
1159 yyextra->isTypedef=false;
1160 addType(yyscanner);
1161 yyextra->current->type += " module";
1162 yyextra->current->fileName = yyextra->fileName;
1163 yyextra->current->startLine = yyextra->yyLineNr;
1164 yyextra->current->startColumn = yyextra->yyColNr;
1165 yyextra->current->bodyLine = yyextra->yyLineNr;
1166 yyextra->current->bodyColumn = yyextra->yyColNr;
1167 yyextra->current->name = name+":"+partition;
1168 lineCount(yyscanner);
1169 }
DString mid(size_t index, size_t len=npos) const
Definition dstring.h:322
size_t find(char c, size_t pos=0) const
Definition dstring.h:243
void createModuleDef(const DString &fileName, int line, size_t column, bool exported, const DString &moduleName, const DString &partitionName=DString())
static ModuleManager & instance()
1170<ModuleName>{MODULE_ID} { // primary module name, e.g. A.B
1171 ModuleManager::instance().createModuleDef(yyextra->fileName,
1172 yyextra->yyLineNr,
1173 yyextra->yyColNr,
1174 yyextra->current->exported,
1175 yytext);
1176 yyextra->current->section = EntryType::makeModuleDoc();
1177 yyextra->isTypedef=false;
1178 addType(yyscanner);
1179 yyextra->current->type += " module";
1180 yyextra->current->fileName = yyextra->fileName;
1181 yyextra->current->startLine = yyextra->yyLineNr;
1182 yyextra->current->startColumn = yyextra->yyColNr;
1183 yyextra->current->bodyLine = yyextra->yyLineNr;
1184 yyextra->current->bodyColumn = yyextra->yyColNr;
1185 yyextra->current->name = yytext;
1186 lineCount(yyscanner);
1187 }
1188<ModuleName>":"{BN}+"private" { // start of private section of the module interface
1189 yyextra->current->exported = yyextra->exported = false;
1190 lineCount(yyscanner);
1191 }
1192<ModuleName>";" { unput(';');
1193 BEGIN(FindMembers);
1194 }
1195<ModuleName>\n { lineCount(yyscanner); }
1196<ModuleName>. {}
1197<ModuleImport>"\""[^"\n]*"\"" { // local header import
1198 ModuleManager::instance().addHeader(yyextra->fileName,
1199 yyextra->yyLineNr,
1200 DString(yytext).mid(1,yyleng-2),
1201 false);
1202 }
void addHeader(const DString &moduleFile, int line, const DString &headerName, bool isSystem)
1203<ModuleImport>"<"[^>\n]*">" { // system header import
1204 ModuleManager::instance().addHeader(yyextra->fileName,
1205 yyextra->yyLineNr,
1206 DString(yytext).mid(1,yyleng-2),
1207 true);
1208 }
1209<ModuleImport>{MODULE_ID}?{BN}*":"{BN}*{MODULE_ID} { // module partition import
1210 DString name = yytext; // can be 'M:P' or ':P'
1211 size_t i = name.find(':');
1212 DString partition = name.mid(i+1).stripWhiteSpace();
1213 name = name.left(i).stripWhiteSpace();
1214 ModuleManager::instance().addImport(yyextra->fileName,
1215 yyextra->yyLineNr,
1216 name,
1217 yyextra->current->exported,
1218 partition);
1219 lineCount(yyscanner);
1220 }
void addImport(const DString &moduleFile, int line, const DString &importName, bool isExported, const DString &partitionName=DString())
1221<ModuleImport>{MODULE_ID} { // module import
1222 ModuleManager::instance().addImport(yyextra->fileName,
1223 yyextra->yyLineNr,
1224 yytext,
1225 yyextra->current->exported);
1226 lineCount(yyscanner);
1227 }
1228<ModuleImport>";" { BEGIN(FindMembers); }
1229<ModuleImport>\n { lineCount(yyscanner); }
1230<ModuleImport>. {}
1231<FindMembers>{B}*"export"{BN}+"{" {
1232 yyextra->current->exported = yyextra->exported = true; // export block
1233 }
1234<FindMembers>{B}*"export"{BN}+ {
1235 if (!yyextra->insideCpp) REJECT;
1236 yyextra->current->exported=true;
1237 }
1238<FindMembers>{B}*"initonly"{BN}+ { if (yyextra->insideJava || yyextra->insideCpp) REJECT;
1239 yyextra->current->type += " initonly ";
1240 if (yyextra->insideCli) yyextra->current->spec.setInitonly(true);
1241 lineCount(yyscanner);
1242 }
1243<FindMembers>{B}*"static"{BN}*/"{" { yyextra->current->type += " static ";
1244 yyextra->current->isStatic = true;
1245 lineCount(yyscanner);
1246 }
1247<FindMembers>{B}*"static"{BN}+ { yyextra->current->type += " static ";
1248 yyextra->current->isStatic = true;
1249 lineCount(yyscanner);
1250 }
1251<FindMembers>{B}*"extern"{BN}+ { if (yyextra->insideJava) REJECT;
1252 yyextra->current->isStatic = false;
1253 yyextra->current->explicitExternal = true;
1254 lineCount(yyscanner);
1255 }
1256<FindMembers>{B}*"const"{BN}+ { if (yyextra->insideCS)
1257 {
1258 yyextra->current->type += " const ";
1259 if (yyextra->insideCS) yyextra->current->isStatic = true;
1260 lineCount(yyscanner);
1261 }
1262 else
1263 {
1264 REJECT;
1265 }
1266 }
1267<FindMembers>{B}*"virtual"{BN}+ { if (yyextra->insideJava) REJECT;
1268 yyextra->current->type += " virtual ";
1269 yyextra->current->virt = Specifier::Virtual;
1270 lineCount(yyscanner);
1271 }
1272<FindMembers>{B}*"constexpr"{BN}+ {
1273 if (yyextra->insideCpp)
1274 {
1275 yyextra->current->spec.setConstExpr(true);
1276 }
1277 REJECT;
1278 }
1279<FindMembers>{B}*"consteval"{BN}+ {
1280 if (yyextra->insideCpp)
1281 {
1282 yyextra->current->spec.setConstEval(true);
1283 }
1284 REJECT;
1285 }
1286<FindMembers>{B}*"constinit"{BN}+ {
1287 if (yyextra->insideCpp)
1288 {
1289 yyextra->current->spec.setConstInit(true);
1290 }
1291 REJECT;
1292 }
1293<FindMembers>{B}*"published"{BN}+ { // UNO IDL published keyword
1294 if (yyextra->insideIDL)
1295 {
1296 lineCount(yyscanner);
1297 yyextra->current->spec.setPublished(true);
1298 }
1299 else
1300 {
1301 REJECT;
1302 }
1303 }
1304<FindMembers>{B}*"sealed"{BN}+ {
1305 if (yyextra->insideCS)
1306 {
1307 yyextra->current->spec.setSealed(true);
1308 }
1309 else
1310 {
1311 REJECT;
1312 }
1313 }
1314<FindMembers>{B}*"abstract"{BN}+ {
1315 if (yyextra->insidePHP || yyextra->insideCS)
1316 {
1317 yyextra->current->spec.setAbstract(true);
1318 }
1319 else
1320 {
1321 if (yyextra->insideCpp) REJECT;
1322 yyextra->current->type += " abstract ";
1323 if (!yyextra->insideJava)
1324 {
1325 yyextra->current->virt = Specifier::Pure;
1326 }
1327 else
1328 {
1329 yyextra->current->spec.setAbstract(true);
1330 }
1331 }
1332 lineCount(yyscanner);
1333 }
1334<FindMembers>{B}*"inline"{BN}+ { if (yyextra->insideJava) REJECT;
1335 yyextra->current->spec.setInline(true);
1336 lineCount(yyscanner);
1337 }
1338<FindMembers>{B}*"mutable"{BN}+ { if (yyextra->insideJava) REJECT;
1339 yyextra->current->spec.setMutable(true);
1340 lineCount(yyscanner);
1341 }
1342<FindMembers>{B}*"thread_local"{BN}+ { if (yyextra->insideJava) REJECT;
1343 yyextra->current->spec.setThreadLocal(true);
1344 lineCount(yyscanner);
1345 }
1346<FindMembers>{B}*"explicit"{BN}+ { if (yyextra->insideJava) REJECT;
1347 yyextra->current->spec.setExplicit(true);
1348 lineCount(yyscanner);
1349 }
1350<FindMembers>{B}*"local"{BN}+ { if (yyextra->insideJava || yyextra->insideCpp) REJECT;
1351 yyextra->current->spec.setLocal(true);
1352 lineCount(yyscanner);
1353 }
1354<FindMembers>{B}*"@required"{BN}+ { // Objective C 2.0 protocol required section
1355 yyextra->current->spec.setOptional(false).setRequired(true);
1356 lineCount(yyscanner);
1357 }
1358<FindMembers>{B}*"@optional"{BN}+ { // Objective C 2.0 protocol optional section
1359 yyextra->current->spec.setRequired(false).setOptional(true);
1360 lineCount(yyscanner);
1361 }
1362 /*
1363<FindMembers>{B}*"import"{BN}+ { // IDL import keyword
1364 BEGIN( NextSemi );
1365 }
1366 */
1367<FindMembers>{B}*"typename"{BN}+ { lineCount(yyscanner); }
1368<FindMembers>{B}*"namespace"{BNopt}/[^a-z_A-Z0-9] { if (yyextra->insideJava) REJECT;
1369 yyextra->isTypedef=false;
1370 yyextra->current->section = EntryType::makeNamespace();
1371 yyextra->current->type = "namespace" ;
1372 yyextra->current->fileName = yyextra->fileName;
1373 yyextra->current->startLine = yyextra->yyLineNr;
1374 yyextra->current->startColumn = yyextra->yyColNr;
1375 yyextra->current->bodyLine = yyextra->yyLineNr;
1376 yyextra->current->bodyColumn = yyextra->yyColNr;
1377 lineCount(yyscanner);
1378 if (yyextra->insidePHP)
1379 {
1380 BEGIN( PackageName );
1381 }
1382 else
1383 {
1384 BEGIN( CompoundName );
1385 }
1386 }
1387<FindMembers>{B}*"module"{BN}+ {
1388 lineCount(yyscanner);
1389 if (yyextra->insideIDL || yyextra->insideSlice)
1390 {
1391 yyextra->isTypedef=false;
1392 yyextra->current->section = EntryType::makeNamespace();
1393 yyextra->current->type = "module" ;
1394 yyextra->current->fileName = yyextra->fileName;
1395 yyextra->current->startLine = yyextra->yyLineNr;
1396 yyextra->current->startColumn = yyextra->yyColNr;
1397 yyextra->current->bodyLine = yyextra->yyLineNr;
1398 yyextra->current->bodyColumn = yyextra->yyColNr;
1399 BEGIN( CompoundName );
1400 }
1401 else if (yyextra->insideD)
1402 {
1403 lineCount(yyscanner);
1404 BEGIN(PackageName);
1405 }
1406 else
1407 {
1408 addType(yyscanner);
1409 yyextra->current->name = DString(yytext).stripWhiteSpace();
1410 }
1411 }
1412<FindMembers>{B}*"library"{BN}+ {
1413 lineCount(yyscanner);
1414 if (yyextra->insideIDL)
1415 {
1416 yyextra->isTypedef=false;
1417 yyextra->current->section = EntryType::makeNamespace();
1418 yyextra->current->type = "library" ;
1419 yyextra->current->fileName = yyextra->fileName;
1420 yyextra->current->startLine = yyextra->yyLineNr;
1421 yyextra->current->startColumn = yyextra->yyColNr;
1422 yyextra->current->bodyLine = yyextra->yyLineNr;
1423 yyextra->current->bodyColumn = yyextra->yyColNr;
1424 BEGIN( CompoundName );
1425 }
1426 else
1427 {
1428 addType(yyscanner);
1429 yyextra->current->name = DString(yytext).stripWhiteSpace();
1430 }
1431 }
1432<FindMembers>{B}*"constants"{BN}+ { // UNO IDL constant group
1433 lineCount(yyscanner);
1434 if (yyextra->insideIDL)
1435 {
1436 yyextra->isTypedef=false;
1437 yyextra->current->section = EntryType::makeNamespace();
1438 yyextra->current->type = "constants";
1439 yyextra->current->fileName = yyextra->fileName;
1440 yyextra->current->startLine = yyextra->yyLineNr;
1441 yyextra->current->startColumn = yyextra->yyColNr;
1442 yyextra->current->bodyLine = yyextra->yyLineNr;
1443 yyextra->current->bodyColumn = yyextra->yyColNr;
1444 BEGIN( CompoundName );
1445 }
1446 else
1447 {
1448 addType(yyscanner);
1449 yyextra->current->name = DString(yytext).stripWhiteSpace();
1450 }
1451 }
1452<FindMembers>{BN}*("service"){BN}+ { // UNO IDL service
1453 lineCount(yyscanner);
1454 if (yyextra->insideIDL)
1455 {
1456 yyextra->isTypedef=false;
1457 yyextra->current->section = EntryType::makeClass();
1458 TypeSpecifier spec = yyextra->current->spec;
1459 yyextra->current->spec = TypeSpecifier().setService(true).
1460 // preserve UNO IDL [optional] or published
1461 setOptional(spec.isOptional()).setPublished(spec.isPublished());
1462 addType(yyscanner);
1463 yyextra->current->type += " service " ;
1464 yyextra->current->fileName = yyextra->fileName;
1465 yyextra->current->startLine = yyextra->yyLineNr;
1466 yyextra->current->bodyLine = yyextra->yyLineNr;
1467 yyextra->current->bodyColumn = yyextra->yyColNr;
1468 BEGIN( CompoundName );
1469 }
1470 else // TODO is addType right? just copy/pasted
1471 {
1472 addType(yyscanner);
1473 yyextra->current->name = DString(yytext).stripWhiteSpace();
1474 }
1475 }
Wrapper class for a number of boolean properties.
Definition types.h:694
1476<FindMembers>{BN}*("singleton"){BN}+ { // UNO IDL singleton
1477 lineCount(yyscanner);
1478 if (yyextra->insideIDL)
1479 {
1480 yyextra->isTypedef=false;
1481 yyextra->current->section = EntryType::makeClass();
1482 TypeSpecifier spec = yyextra->current->spec;
1483 yyextra->current->spec = TypeSpecifier().setSingleton(true).
1484 setPublished(spec.isPublished()); // preserve
1485 addType(yyscanner);
1486 yyextra->current->type += " singleton " ;
1487 yyextra->current->fileName = yyextra->fileName;
1488 yyextra->current->startLine = yyextra->yyLineNr;
1489 yyextra->current->bodyLine = yyextra->yyLineNr;
1490 yyextra->current->bodyColumn = yyextra->yyColNr;
1491 BEGIN( CompoundName );
1492 }
1493 else // TODO is addType right? just copy/pasted
1494 {
1495 addType(yyscanner);
1496 yyextra->current->name = DString(yytext).stripWhiteSpace();
1497 }
1498 }
1499<FindMembers>{BN}*((("disp")?"interface")|"valuetype"){BN}+ { // M$/Corba/UNO IDL/Java/Slice interface
1500 lineCount(yyscanner);
1501 if (yyextra->insideIDL || yyextra->insideJava || yyextra->insideCS || yyextra->insideD || yyextra->insidePHP || yyextra->insideSlice)
1502 {
1503 yyextra->isTypedef=false;
1504 yyextra->current->section = EntryType::makeClass();
1505 TypeSpecifier spec = yyextra->current->spec;
1506 yyextra->current->spec = TypeSpecifier().setInterface(true).
1507 // preserve UNO IDL [optional], published, Slice local
1508 setOptional(spec.isOptional()).
1509 setPublished(spec.isPublished()).
1510 setLocal(spec.isLocal());
1511 addType(yyscanner);
1512 yyextra->current->type += " interface" ;
1513 yyextra->current->fileName = yyextra->fileName;
1514 yyextra->current->startLine = yyextra->yyLineNr;
1515 yyextra->current->startColumn = yyextra->yyColNr;
1516 yyextra->current->bodyLine = yyextra->yyLineNr;
1517 yyextra->current->bodyColumn = yyextra->yyColNr;
1518 setJavaProtection(yyscanner);
1519 BEGIN( CompoundName );
1520 }
1521 else
1522 {
1523 addType(yyscanner);
1524 yyextra->current->name = DString(yytext).stripWhiteSpace();
1525 }
1526 }
1527<FindMembers>{B}*"@implementation"{BN}+ { // Objective-C class implementation
1528 lineCount(yyscanner);
1529 yyextra->isTypedef=false;
1530 yyextra->current->section = EntryType::makeObjcImpl();
1531 yyextra->language = yyextra->current->lang = SrcLangExt::ObjC;
1532 yyextra->insideObjC = true;
1533 yyextra->current->protection = yyextra->protection = Protection::Public ;
1534 addType(yyscanner);
1535 yyextra->current->type += " implementation" ;
1536 yyextra->current->fileName = yyextra->fileName;
1537 yyextra->current->startLine = yyextra->yyLineNr;
1538 yyextra->current->bodyLine = yyextra->yyLineNr;
1539 yyextra->current->bodyColumn = yyextra->yyColNr;
1540 BEGIN( CompoundName );
1541 }
1542<FindMembers>{B}*"@interface"{BN}+ { // Objective-C class interface, or Java attribute
1543 lineCount(yyscanner);
1544 yyextra->isTypedef=false;
1545 yyextra->current->section = EntryType::makeClass();
1546 yyextra->current->spec = TypeSpecifier().setInterface(true);
1547 if (!yyextra->insideJava)
1548 {
1549 yyextra->language = yyextra->current->lang = SrcLangExt::ObjC;
1550 yyextra->insideObjC = true;
1551 }
1552 yyextra->current->protection = yyextra->protection = Protection::Public ;
1553 addType(yyscanner);
1554 yyextra->current->type += " interface" ;
1555 yyextra->current->fileName = yyextra->fileName;
1556 yyextra->current->startLine = yyextra->yyLineNr;
1557 yyextra->current->startColumn = yyextra->yyColNr;
1558 yyextra->current->bodyLine = yyextra->yyLineNr;
1559 yyextra->current->bodyColumn = yyextra->yyColNr;
1560 BEGIN( CompoundName );
1561 }
1562<FindMembers>{B}*"@protocol"{BN}+ { // Objective-C protocol definition
1563 lineCount(yyscanner);
1564 yyextra->isTypedef=false;
1565 yyextra->current->section = EntryType::makeClass();
1566 yyextra->current->spec = TypeSpecifier().setProtocol(true);
1567 yyextra->language = yyextra->current->lang = SrcLangExt::ObjC;
1568 yyextra->insideObjC = true;
1569 yyextra->current->protection = yyextra->protection = Protection::Public ;
1570 addType(yyscanner);
1571 yyextra->current->type += " protocol" ;
1572 yyextra->current->fileName = yyextra->fileName;
1573 yyextra->current->startLine = yyextra->yyLineNr;
1574 yyextra->current->startColumn = yyextra->yyColNr;
1575 yyextra->current->bodyLine = yyextra->yyLineNr;
1576 yyextra->current->bodyColumn = yyextra->yyColNr;
1577 BEGIN( CompoundName );
1578 }
1579<FindMembers>{B}*"exception"{BN}+ { // Corba IDL/Slice exception
1580 if (yyextra->insideJava || yyextra->insideCpp) REJECT;
1581 yyextra->isTypedef=false;
1582 yyextra->current->section = EntryType::makeClass();
1583 TypeSpecifier spec = yyextra->current->spec;
1584 // preserve UNO IDL, Slice local
1585 yyextra->current->spec = TypeSpecifier().setException(true).
1586 setPublished(spec.isPublished()).setLocal(spec.isLocal());
1587 addType(yyscanner);
1588 yyextra->current->type += " exception" ;
1589 yyextra->current->fileName = yyextra->fileName;
1590 yyextra->current->startLine = yyextra->yyLineNr;
1591 yyextra->current->startColumn = yyextra->yyColNr;
1592 yyextra->current->bodyLine = yyextra->yyLineNr;
1593 yyextra->current->bodyColumn = yyextra->yyColNr;
1594 lineCount(yyscanner);
1595 BEGIN( CompoundName );
1596 }
1597<FindMembers>"@class" | // for Objective C class declarations
1598<FindMembers>{B}*{TYPEDEFPREFIX}"class{" |
1599<FindMembers>{B}*{TYPEDEFPREFIX}"class"{BN}+ {
1600 DString decl = yytext;
1601 yyextra->isTypedef = decl.find("typedef") !=DString::npos;
1602 bool isConst = decl.find("const") !=DString::npos;
1603 bool isVolatile = decl.find("volatile")!=DString::npos;
1604 yyextra->current->section = EntryType::makeClass();
1605 addType(yyscanner);
1606 if (yyextra->insidePHP && yyextra->current->spec.isAbstract())
1607 {
1608 // convert Abstract to AbstractClass
1609 yyextra->current->spec.setAbstract(false).setAbstractClass(true);
1610 }
1611 if (yyextra->insideSlice && yyextra->current->spec.isLocal())
1612 {
1613 yyextra->current->spec.setLocal(true);
1614 }
1615 if (isConst)
1616 {
1617 yyextra->current->type += " const";
1618 }
1619 else if (isVolatile)
1620 {
1621 yyextra->current->type += " volatile";
1622 }
1623 yyextra->current->type += " class" ;
1624 yyextra->current->fileName = yyextra->fileName;
1625 yyextra->current->startLine = yyextra->yyLineNr;
1626 yyextra->current->startColumn = yyextra->yyColNr;
1627 yyextra->current->bodyLine = yyextra->yyLineNr;
1628 yyextra->current->bodyColumn = yyextra->yyColNr;
1629 if (yytext[0]=='@')
1630 {
1631 yyextra->language = yyextra->current->lang = SrcLangExt::ObjC;
1632 yyextra->insideObjC = true;
1633 }
1634 lineCount(yyscanner) ;
1635 if (yytext[yyleng-1]=='{') unput('{');
1636 BEGIN( CompoundName ) ;
1637 }
static constexpr size_t npos
value used to indicate 'not found' or 'to the end of the string', matching std::string::npos
Definition dstring.h:182
1638<FindMembers>{B}*"value class{" | // C++/CLI extension
1639<FindMembers>{B}*"value class"{BN}+ {
1640 yyextra->isTypedef=false;
1641 yyextra->current->section = EntryType::makeClass();
1642 yyextra->current->spec = TypeSpecifier().setValue(true);
1643 addType(yyscanner);
1644 yyextra->current->type += " value class" ;
1645 yyextra->current->fileName = yyextra->fileName;
1646 yyextra->current->startLine = yyextra->yyLineNr;
1647 yyextra->current->startColumn = yyextra->yyColNr;
1648 yyextra->current->bodyLine = yyextra->yyLineNr;
1649 yyextra->current->bodyColumn = yyextra->yyColNr;
1650 lineCount(yyscanner) ;
1651 if (yytext[yyleng-1]=='{') unput('{');
1652 BEGIN( CompoundName ) ;
1653 }
1654<FindMembers>{B}*"ref class{" | // C++/CLI extension
1655<FindMembers>{B}*"ref class"{BN}+ {
1656 yyextra->isTypedef=false;
1657 yyextra->current->section = EntryType::makeClass();
1658 yyextra->current->spec = TypeSpecifier().setRef(true);
1659 addType(yyscanner);
1660 yyextra->current->type += " ref class" ;
1661 yyextra->current->fileName = yyextra->fileName;
1662 yyextra->current->startLine = yyextra->yyLineNr;
1663 yyextra->current->startColumn = yyextra->yyColNr;
1664 yyextra->current->bodyLine = yyextra->yyLineNr;
1665 yyextra->current->bodyColumn = yyextra->yyColNr;
1666 lineCount(yyscanner) ;
1667 if (yytext[yyleng-1]=='{') unput('{');
1668 BEGIN( CompoundName ) ;
1669 }
1670<FindMembers>{B}*"interface class{" | // C++/CLI extension
1671<FindMembers>{B}*"interface class"{BN}+ {
1672 yyextra->isTypedef=false;
1673 yyextra->current->section = EntryType::makeClass();
1674 yyextra->current->spec = TypeSpecifier().setInterface(true);
1675 addType(yyscanner);
1676 yyextra->current->type += " interface class" ;
1677 yyextra->current->fileName = yyextra->fileName;
1678 yyextra->current->startLine = yyextra->yyLineNr;
1679 yyextra->current->startColumn = yyextra->yyColNr;
1680 yyextra->current->bodyLine = yyextra->yyLineNr;
1681 yyextra->current->bodyColumn = yyextra->yyColNr;
1682 lineCount(yyscanner) ;
1683 if (yytext[yyleng-1]=='{') unput('{');
1684 BEGIN( CompoundName ) ;
1685 }
1686<FindMembers>{B}*"coclass"{BN}+ {
1687 if (yyextra->insideIDL)
1688 {
1689 yyextra->isTypedef=false;
1690 yyextra->current->section = EntryType::makeClass();
1691 addType(yyscanner);
1692 yyextra->current->type += " coclass" ;
1693 yyextra->current->fileName = yyextra->fileName;
1694 yyextra->current->startLine = yyextra->yyLineNr;
1695 yyextra->current->startColumn = yyextra->yyColNr;
1696 yyextra->current->bodyLine = yyextra->yyLineNr;
1697 yyextra->current->bodyColumn = yyextra->yyColNr;
1698 lineCount(yyscanner) ;
1699 BEGIN( CompoundName ) ;
1700 }
1701 else
1702 {
1703 addType(yyscanner);
1704 yyextra->current->name = yytext;
1705 yyextra->current->name = yyextra->current->name.stripWhiteSpace();
1706 lineCount(yyscanner);
1707 }
1708 }
1709<FindMembers>{B}*{TYPEDEFPREFIX}"struct{" |
1710<FindMembers>{B}*{TYPEDEFPREFIX}"struct"/{BN}+ {
1711 if (yyextra->insideJava) REJECT;
1712 DString decl = yytext;
1713 yyextra->isTypedef = decl.find("typedef") !=DString::npos;
1714 bool isConst = decl.find("const") !=DString::npos;
1715 bool isVolatile = decl.find("volatile")!=DString::npos;
1716 yyextra->current->section = EntryType::makeClass() ;
1717 TypeSpecifier spec = yyextra->current->spec;
1718 yyextra->current->spec = TypeSpecifier().setStruct(true).
1719 // preserve UNO IDL & Inline attributes, Slice local
1720 setPublished(spec.isPublished()).
1721 setInline(spec.isInline()).
1722 setLocal(spec.isLocal());
1723 // bug 582676: can be a struct nested in an interface so keep yyextra->insideObjC state
1724 //yyextra->current->objc = yyextra->insideObjC = false;
1725 addType(yyscanner);
1726 if (isConst)
1727 {
1728 yyextra->current->type += " const";
1729 }
1730 else if (isVolatile)
1731 {
1732 yyextra->current->type += " volatile";
1733 }
1734 yyextra->current->type += " struct" ;
1735 yyextra->current->fileName = yyextra->fileName;
1736 yyextra->current->startLine = yyextra->yyLineNr;
1737 yyextra->current->startColumn = yyextra->yyColNr;
1738 yyextra->current->bodyLine = yyextra->yyLineNr;
1739 yyextra->current->bodyColumn = yyextra->yyColNr;
1740 lineCount(yyscanner) ;
1741 if (yytext[yyleng-1]=='{') unput('{');
1742 BEGIN( CompoundName ) ;
1743 }
1744<FindMembers>{B}*"value struct{" | // C++/CLI extension
1745<FindMembers>{B}*"value struct"{BN}+ {
1746 yyextra->isTypedef=false;
1747 yyextra->current->section = EntryType::makeClass();
1748 yyextra->current->spec = TypeSpecifier().setStruct(true).setValue(true);
1749 addType(yyscanner);
1750 yyextra->current->type += " value struct" ;
1751 yyextra->current->fileName = yyextra->fileName;
1752 yyextra->current->startLine = yyextra->yyLineNr;
1753 yyextra->current->startColumn = yyextra->yyColNr;
1754 yyextra->current->bodyLine = yyextra->yyLineNr;
1755 yyextra->current->bodyColumn = yyextra->yyColNr;
1756 lineCount(yyscanner) ;
1757 if (yytext[yyleng-1]=='{') unput('{');
1758 BEGIN( CompoundName ) ;
1759 }
1760<FindMembers>{B}*"ref struct{" | // C++/CLI extension
1761<FindMembers>{B}*"ref struct"{BN}+ {
1762 yyextra->isTypedef=false;
1763 yyextra->current->section = EntryType::makeClass();
1764 yyextra->current->spec = TypeSpecifier().setStruct(true).setRef(true);
1765 addType(yyscanner);
1766 yyextra->current->type += " ref struct" ;
1767 yyextra->current->fileName = yyextra->fileName;
1768 yyextra->current->startLine = yyextra->yyLineNr;
1769 yyextra->current->startColumn = yyextra->yyColNr;
1770 yyextra->current->bodyLine = yyextra->yyLineNr;
1771 yyextra->current->bodyColumn = yyextra->yyColNr;
1772 lineCount(yyscanner) ;
1773 if (yytext[yyleng-1]=='{') unput('{');
1774 BEGIN( CompoundName ) ;
1775 }
1776<FindMembers>{B}*"interface struct{" | // C++/CLI extension
1777<FindMembers>{B}*"interface struct"{BN}+ {
1778 yyextra->isTypedef=false;
1779 yyextra->current->section = EntryType::makeClass();
1780 yyextra->current->spec = TypeSpecifier().setStruct(true).setInterface(true);
1781 addType(yyscanner);
1782 yyextra->current->type += " interface struct";
1783 yyextra->current->fileName = yyextra->fileName;
1784 yyextra->current->startLine = yyextra->yyLineNr;
1785 yyextra->current->startColumn = yyextra->yyColNr;
1786 yyextra->current->bodyLine = yyextra->yyLineNr;
1787 yyextra->current->bodyColumn = yyextra->yyColNr;
1788 lineCount(yyscanner) ;
1789 if (yytext[yyleng-1]=='{') unput('{');
1790 BEGIN( CompoundName ) ;
1791 }
1792<FindMembers>{B}*{TYPEDEFPREFIX}"union{" |
1793<FindMembers>{B}*{TYPEDEFPREFIX}"union"{BN}+ {
1794 if (yyextra->insideJava) REJECT;
1795 DString decl=yytext;
1796 yyextra->isTypedef = decl.find("typedef") !=DString::npos;
1797 bool isConst = decl.find("const") !=DString::npos;
1798 bool isVolatile = decl.find("volatile")!=DString::npos;
1799 yyextra->current->section = EntryType::makeClass();
1800 yyextra->current->spec = TypeSpecifier().setUnion(true);
1801 // bug 582676: can be a struct nested in an interface so keep yyextra->insideObjC state
1802 //yyextra->current->objc = yyextra->insideObjC = false;
1803 addType(yyscanner);
1804 if (isConst)
1805 {
1806 yyextra->current->type += " const";
1807 }
1808 else if (isVolatile)
1809 {
1810 yyextra->current->type += " volatile";
1811 }
1812 yyextra->current->type += " union" ;
1813 yyextra->current->fileName = yyextra->fileName;
1814 yyextra->current->startLine = yyextra->yyLineNr;
1815 yyextra->current->startColumn = yyextra->yyColNr;
1816 yyextra->current->bodyLine = yyextra->yyLineNr;
1817 yyextra->current->bodyColumn = yyextra->yyColNr;
1818 lineCount(yyscanner) ;
1819 if (yytext[yyleng-1]=='{') unput('{');
1820 BEGIN( CompoundName ) ;
1821 }
1822<FindMembers>{B}*{TYPEDEFPREFIX}{IDLATTR}?"enum"({BN}+("class"|"struct"))?"{" |
1823<FindMembers>{B}*{TYPEDEFPREFIX}{IDLATTR}?"enum"({BN}+("class"|"struct"))?{BN}+ { // for IDL: typedef [something] enum
1824 DString text=yytext;
1825 yyextra->isTypedef = text.find("typedef")!=DString::npos;
1826 bool isStrongEnum = text.find("class") !=DString::npos || yyextra->insideCS;
1827 bool isEnumSytruct = text.find("struct") !=DString::npos;
1828 if (yyextra->insideJava)
1829 {
1830 yyextra->current->section = EntryType::makeClass();
1831 setJavaProtection(yyscanner);
1832 yyextra->current->spec = TypeSpecifier().setEnum(true);
1833 }
1834 else
1835 {
1836 yyextra->current->section = EntryType::makeEnum() ;
1837 }
1838 addType(yyscanner);
1839 yyextra->current->type += " enum";
1840 if (isStrongEnum)
1841 {
1842 yyextra->current->spec.setStrong(true);
1843 }
1844 if (isEnumSytruct)
1845 {
1846 yyextra->current->spec.setStrong(true).setEnumStruct(true);
1847 }
1848 yyextra->current->fileName = yyextra->fileName;
1849 yyextra->current->startLine = yyextra->yyLineNr;
1850 yyextra->current->startColumn = yyextra->yyColNr;
1851 yyextra->current->bodyLine = yyextra->yyLineNr;
1852 yyextra->current->bodyColumn = yyextra->yyColNr;
1853 lineCount(yyscanner) ;
1854 if (yytext[yyleng-1]=='{') unput('{');
1855 BEGIN( CompoundName ) ;
1856 }
1857<FindMembers>{B}*"concept"{BN}+ { // C++20 concept
1858 if (yyextra->insideJava) REJECT;
1859 yyextra->isTypedef=false;
1860 yyextra->current->section = EntryType::makeConcept();
1861 addType(yyscanner);
1862 yyextra->current->type += " concept";
1863 yyextra->current->fileName = yyextra->fileName;
1864 yyextra->current->startLine = yyextra->yyLineNr;
1865 yyextra->current->startColumn = yyextra->yyColNr;
1866 yyextra->current->bodyLine = yyextra->yyLineNr;
1867 yyextra->current->bodyColumn = yyextra->yyColNr;
1868 yyextra->current->args = yyextra->fullArgString;
1869 yyextra->keepComment = true;
1870 lineCount(yyscanner) ;
1871 BEGIN( ConceptName ) ;
1872 }
1873<Operator>"("{BN}*")"({BN}*"<"[^>]*">"){BNopt}/"(" { // A::operator()<int>(int arg)
1874 lineCount(yyscanner);
1875 yyextra->current->name += "()";
1876 BEGIN( FindMembers );
1877 }
1878<Operator>"("{BN}*")"{BNopt}/("[["[^\‍]]*"]]"){BNopt}"(" {
1879 lineCount(yyscanner);
1880 yyextra->current->name += yytext ;
1881 yyextra->current->name = yyextra->current->name.simplifyWhiteSpace();
1882 BEGIN( FindMembers ) ;
1883 }
1884<Operator>"("{BN}*")"{BNopt}/"(" {
1885 lineCount(yyscanner);
1886 yyextra->current->name += yytext ;
1887 yyextra->current->name = yyextra->current->name.simplifyWhiteSpace();
1888 BEGIN( FindMembers ) ;
1889 }
1890<Operator>";" { // can occur when importing members
1891 unput(';');
1892 BEGIN( FindMembers ) ;
1893 }
1894<Operator>[^(] {
1895 lineCount(yyscanner);
1896 yyextra->current->name += *yytext ;
1897 }
1898<Operator>"<"({B}*{ID}{B}*(","{B}*{BN})*{B}*)?">" { /* skip guided templ specifiers */
1899 if (!yyextra->current->type.startsWith("friend "))
1900 {
1901 yyextra->current->name += yytext;
1902 }
1903 }
1904<Operator>"(" {
1905 yyextra->current->name = yyextra->current->name.simplifyWhiteSpace();
1906 unput(*yytext);
1907 BEGIN( FindMembers ) ;
1908 }
1909<FindMembers>("template"|"generic")({BN}*)"<"/[>]? { // generic is a C++/CLI extension
1910 lineCount(yyscanner);
1911 ArgumentList al;
1912 yyextra->current->tArgLists.push_back(al);
1913 yyextra->currentArgumentList = &yyextra->current->tArgLists.back();
1914 yyextra->templateStr="<";
1915 yyextra->fullArgString = yyextra->templateStr;
1916 yyextra->copyArgString = &yyextra->templateStr;
1917 yyextra->currentArgumentContext = FindMembers;
1918 BEGIN( ReadTempArgs );
1919 }
void push_back(const Argument &a)
Definition arguments.h:103
1920<FindMembers>"namespace"{BN}+/{ID}{BN}*"=" { // namespace alias
1921 if (yyextra->insideJava) REJECT;
1922 lineCount(yyscanner);
1923 BEGIN( NSAliasName );
1924 }
1925<NSAliasName>{ID} {
1926 yyextra->aliasName = yytext;
1927 BEGIN( NSAliasArg );
1928 }
1929<NSAliasArg>({ID}"::")*{ID} {
1930 //printf("Inserting namespace alias %s::%s->%s\n",qPrint(yyextra->current_root->name),qPrint(yyextra->aliasName),yytext);
1931 std::string ctx = yyextra->current_root->name.str();
1932 if (ctx.empty())
1933 {
1934 Doxygen::namespaceAliasMap.emplace(yyextra->aliasName.str(),NamespaceAliasInfo(std::string(yytext),std::string()));
1935 }
1936 else
1937 {
1938 Doxygen::namespaceAliasMap.emplace(ctx+"::"+yyextra->aliasName.str(),NamespaceAliasInfo(std::string(yytext),ctx));
1939 }
1940 }
static NamespaceAliasInfoMap namespaceAliasMap
Definition doxygen.h:106
1941<NSAliasArg>";" {
1942 BEGIN( FindMembers );
1943 }
1944<PHPUse>({ID}{BN}*"\\"{BN}*)*{ID}/{BN}+"as" {
1945 lineCount(yyscanner);
1946 yyextra->aliasName=yytext;
1947 BEGIN(PHPUseAs);
1948 }
1949<PHPUse>({ID}{BN}*"\\"{BN}*)*{ID} {
1950 lineCount(yyscanner);
1951 yyextra->current->name=removeRedundantWhiteSpace(substitute(yytext,"\\","::"));
1952 //printf("PHP: adding use relation: %s\n",qPrint(yyextra->current->name));
1953 yyextra->current->fileName = yyextra->fileName;
1954 // add a using declaration
1955 yyextra->current->section = EntryType::makeUsingDecl();
1956 yyextra->current_root->copyToSubEntry(yyextra->current);
1957 // also add it as a using directive
1958 yyextra->current->section = EntryType::makeUsingDir();
1959 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
1960 initEntry(yyscanner);
1961 yyextra->aliasName.clear();
1962 }
DString removeRedundantWhiteSpace(const DString &s)
Definition util.cpp:427
1963<PHPUseAs>{BN}+"as"{BN}+ {
1964 lineCount(yyscanner);
1965 }
1966<PHPUseAs>{PHPUSEKW} {
1967 }
1968<PHPUseAs>{ID} {
1969 //printf("PHP: adding use as relation: %s->%s\n",yytext,qPrint(yyextra->aliasName));
1970 if (!yyextra->aliasName.empty())
1971 {
1972 std::string aliasValue = removeRedundantWhiteSpace(substitute(yyextra->aliasName,"\\","::")).str();
1973 Doxygen::namespaceAliasMap.emplace(yytext,NamespaceAliasInfo(aliasValue));
1974 }
1975 yyextra->aliasName.clear();
1976 }
const std::string & str() const
Definition dstring.h:649
1977<PHPUse,PHPUseAs>[,;] {
1978 if (*yytext==',')
1979 {
1980 BEGIN(PHPUse);
1981 }
1982 else
1983 {
1984 BEGIN(FindMembers);
1985 }
1986 }
1987<JavaImport>({ID}{BN}*"."{BN}*)+"*" { // package import => add as a using directive
1988 lineCount(yyscanner);
1989 DString scope=yytext;
1990 yyextra->current->name=removeRedundantWhiteSpace(substitute(scope.left(scope.length()-1),".","::"));
1991 yyextra->current->fileName = yyextra->fileName;
1992 bool ambig = false;
1993 FileDef *incFd = Doxygen::inputNameLinkedMap->findFileDef(yyextra->fileName,ambig);
1994 if (incFd)
1995 {
1996 incFd->addIncludeDependency(nullptr,scope,IncludeKind::ImportModule);
1997 }
1998 yyextra->current->section = EntryType::makeUsingDir();
1999 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
2000 initEntry(yyscanner);
2001 BEGIN(Using);
2002 }
static FileNameLinkedMap * inputNameLinkedMap
Definition doxygen.h:97
A model of a file symbol.
Definition filedef.h:97
virtual void addIncludeDependency(const FileDef *fd, const DString &incName, IncludeKind kind)=0
FileDef * findFileDef(const DString &n, bool &ambig) const
Returns the file definition in fnMap that matches the file name n.
Definition filename.cpp:38
@ ImportModule
Definition filedef.h:52
2003<JavaImport>({ID}{BN}*"."{BN}*)+{ID} { // class import => add as a using declaration
2004 lineCount(yyscanner);
2005 DString scope=yytext;
2006 yyextra->current->name=removeRedundantWhiteSpace(substitute(scope,".","::"));
2007 yyextra->current->fileName = yyextra->fileName;
2008 bool ambig = false;
2009 FileDef *fromFd = Doxygen::inputNameLinkedMap->findFileDef(yyextra->fileName,ambig);
2010 FileDef *toFd = Doxygen::inputNameLinkedMap->findFileDef(scope,ambig);
2011 if (fromFd)
2012 {
2014 }
2015 if (toFd && fromFd)
2016 {
2018 }
2019 if (yyextra->insideD)
2020 {
2021 yyextra->current->section = EntryType::makeUsingDir();
2022 }
2023 else
2024 {
2025 //printf("import name = %s -> %s\n",yytext,qPrint(yyextra->current->name));
2026 yyextra->current->section = EntryType::makeUsingDecl();
2027 }
2028 yyextra->previous = yyextra->current;
2029 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
2030 initEntry(yyscanner);
2031 BEGIN(Using);
2032 }
virtual const DString & docName() const =0
virtual void addIncludedByDependency(const FileDef *fd, const DString &incName, IncludeKind kind)=0
2033<IDLImport>"\""[^"]*"\"" {
2034 DString fileName(&yytext[1],yyleng-2);
2035 bool ambig = false;
2036 FileDef *fromFd = Doxygen::inputNameLinkedMap->findFileDef(yyextra->fileName,ambig);
2037 FileDef *toFd = Doxygen::inputNameLinkedMap->findFileDef(fileName,ambig);
2038 if (fromFd)
2039 {
2040 fromFd->addIncludeDependency(toFd,fileName,IncludeKind::ImportModule);
2041 }
2042 if (toFd && fromFd)
2043 {
2045 }
2046 }
2047<IDLImport>";" {
2048 BEGIN(FindMembers);
2049 }
2050<FindMembers>"using"{BN}+/("::"{ID}("::"{ID})*)? {
2051 if (yyextra->insideJava) REJECT;
2052 yyextra->current->startLine=yyextra->yyLineNr;
2053 yyextra->current->startColumn = yyextra->yyColNr;
2054 lineCount(yyscanner);
2055 BEGIN(Using);
2056 }
2057<Using>"namespace"{BN}+ { lineCount(yyscanner); BEGIN(UsingDirective); }
2058<Using>("::")?({ID}{BN}*("::"|"."){BN}*)*({ID}|{OPERATOR}|{FUNCOP}) {
2059 lineCount(yyscanner);
2060 yyextra->current->name=yytext;
2061 yyextra->current->fileName = yyextra->fileName;
2062 yyextra->current->section = EntryType::makeUsingDecl();
2063 yyextra->current->startLine = yyextra->yyLineNr;
2064 yyextra->usingNewVarNeeded = true;
2065 if (yyextra->insideCS) /* Hack: in C# a using declaration and
2066 directive have the same syntax, so we
2067 also add it as a using directive here
2068 */
2069 {
2070 yyextra->current->name=yytext;
2071 yyextra->current->fileName = yyextra->fileName;
2072 yyextra->current->startLine = yyextra->yyLineNr;
2073 yyextra->current->startColumn = yyextra->yyColNr;
2074 yyextra->current->section = EntryType::makeUsingDir();
2075 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
2076 initEntry(yyscanner);
2077 }
2078 BEGIN(Using);
2079 }
2080<Using>({ID}{BN}*("::"|"."){BN}*)*({ID}|{OPERATOR}){BN}*"=" { // C++11 style using alias
2081 yyextra->current->name=DString(yytext).left(yyleng-1).stripWhiteSpace();
2082 yyextra->current->fileName = yyextra->fileName;
2083 yyextra->current->section = EntryType::makeUsingDecl();
2084 yyextra->current->startLine = yyextra->yyLineNr;
2085 yyextra->current->bodyLine = yyextra->yyLineNr;
2086 yyextra->current->bodyColumn = yyextra->yyColNr;
2087 yyextra->lastInitializerContext = UsingAlias;
2088 yyextra->sharpCount=0;
2089 yyextra->initBracketCount=0;
2090 storeClangId(yyscanner,yyextra->current->name.data());
2091 BEGIN(ReadInitializer);
2092 }
2093<Using>";" {
2094 if (yyextra->usingNewVarNeeded)
2095 {
2096 yyextra->previous = yyextra->current;
2097 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
2098 initEntry(yyscanner);
2099 yyextra->usingNewVarNeeded = false;
2100 }
2101 BEGIN(FindMembers);
2102 }
2103<Using>{BN}*"=" {
2104 yyextra->lastInitializerContext = UsingAlias;
2105 yyextra->sharpCount=0;
2106 yyextra->initBracketCount=0;
2107 storeClangId(yyscanner,yyextra->current->name.data());
2108 yyextra->usingNewVarNeeded = false;
2109 BEGIN(ReadInitializer);
2110 }
2111<Using>{B}*{CCS} {
2112 yyextra->lastCContext = YY_START ;
2113 BEGIN( SkipComment ) ;
2114 }
2115<Using>{B}*{CPPC} {
2116 yyextra->lastCContext = YY_START ;
2117 BEGIN( SkipCxxComment ) ;
2118 }
2119<Using>{B}*
2120<Using>. {
2121 if (yyextra->usingNewVarNeeded)
2122 {
2123 yyextra->previous = yyextra->current;
2124 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
2125 initEntry(yyscanner);
2126 yyextra->usingNewVarNeeded = false;
2127 }
2128 }
2129<UsingAlias>";" {
2130 yyextra->current->section = EntryType::makeVariable();
2131 DString init = yyextra->current->initializer.str();
2132 init.stripPrefix("class ");
2133 init.stripPrefix("struct ");
2134 init = init.stripWhiteSpace();
2135 yyextra->current->type = "typedef "+init;
2136 yyextra->current->args.clear();
2137 yyextra->current->spec.setAlias(true);
2138 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
2139 initEntry(yyscanner);
2140 BEGIN(FindMembers);
2141 }
void init()
2142<UsingAlias>. {
2143 yyextra->current->initializer << yytext;
2144 }
2145<UsingAlias>\n {
2146 yyextra->current->initializer << yytext;
2147 lineCount(yyscanner);
2148 }
2149<UsingDirective>{SCOPENAME} { yyextra->current->name=removeRedundantWhiteSpace(yytext);
2150 yyextra->current->fileName = yyextra->fileName;
2151 yyextra->current->section = EntryType::makeUsingDir();
2152 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
2153 initEntry(yyscanner);
2154 yyextra->usingNewVarNeeded = false;
2155 BEGIN(Using);
2156 }
2157<FindMembers>{SCOPENAME}{BN}*"<>" { // guided template decl
2158 DString n=yytext;
2159 addType(yyscanner);
2160 yyextra->current->name=n.left(n.length()-2);
2161 }
2162<FindMembers>{SCOPENAME}{BNopt}/"<" { // Note: this could be a return type!
2163 DString name = DString(yytext).stripWhiteSpace();
2164 if (yyextra->insideCpp && name=="import") REJECT; // C++20 module header import
2165 yyextra->roundCount=0;
2166 yyextra->sharpCount=0;
2167 lineCount(yyscanner);
2168 addType(yyscanner);
2169 yyextra->current->name=name;
2170 //yyextra->current->scopeSpec.clear();
2171 // yyextra->currentTemplateSpec = &yyextra->current->scopeSpec;
2172 if (nameIsOperator(yyextra->current->name))
2173 BEGIN( Operator );
2174 else
2175 BEGIN( EndTemplate );
2176 }
2177<FindMemberName>{SCOPENAME}{BNopt}/"<" {
2178 yyextra->sharpCount=0;
2179 yyextra->roundCount=0;
2180 lineCount(yyscanner);
2181 yyextra->current->name+=((DString)yytext).stripWhiteSpace();
2182 //yyextra->current->memberSpec.clear();
2183 // yyextra->currentTemplateSpec = &yyextra->current->memberSpec;
2184 if (nameIsOperator(yyextra->current->name))
2185 BEGIN( Operator );
2186 else
2187 BEGIN( EndTemplate );
2188 }
std::string_view stripWhiteSpace(std::string_view s)
Given a string view s, returns a new, narrower view on that string, skipping over any leading or trai...
Definition stringutil.h:75
2189<EndTemplate>"<<<" {
2190 if (!yyextra->insidePHP)
2191 {
2192 REJECT;
2193 }
2194 else
2195 {
2196 yyextra->lastHereDocContext = YY_START;
2197 BEGIN(HereDoc);
2198 }
2199 }
2200<ClassTemplSpec,EndTemplate>("<<"|"<=") {
2201 yyextra->current->name+=yytext;
2202 // *yyextra->currentTemplateSpec+=yytext;
2203 }
2204<EndTemplate>"<" {
2205 if (yyextra->roundCount==0)
2206 {
2207 // *yyextra->currentTemplateSpec+='<';
2208 yyextra->sharpCount++;
2209 }
2210 yyextra->current->name+=yytext;
2211 }
2212<ClassTemplSpec,EndTemplate>">=" {
2213 yyextra->current->name+=yytext;
2214 }
2215<ClassTemplSpec,EndTemplate>(">>") {
2216 if (yyextra->insideJava || yyextra->insideCS || yyextra->insideCli || yyextra->roundCount==0)
2217 {
2218 unput('>');
2219 unput(' ');
2220 unput('>');
2221 }
2222 else
2223 {
2224 yyextra->current->name+=yytext;
2225 }
2226 // *yyextra->currentTemplateSpec+=yytext;
2227 }
2228<EndTemplate>">" {
2229 yyextra->current->name+='>';
2230 // *yyextra->currentTemplateSpec+='>';
2231 if (yyextra->roundCount==0 && --yyextra->sharpCount<=0)
2232 {
2233 yyextra->current->name = yyextra->current->name.simplifyWhiteSpace();
2234 //printf("Found %s\n",qPrint(yyextra->current->name));
2235 BEGIN(FindMembers);
2236 }
2237 }
2238<EndTemplate>">"{BN}*"(" {
2239 lineCount(yyscanner);
2240 yyextra->current->name+='>';
2241 // *yyextra->currentTemplateSpec+='>';
2242 if (yyextra->roundCount==0)
2243 {
2244 --yyextra->sharpCount;
2245 }
2246 if (yyextra->roundCount==0 && yyextra->sharpCount<=0)
2247 {
2248 yyextra->current->bodyLine = yyextra->yyLineNr;
2249 yyextra->current->bodyColumn = yyextra->yyColNr;
2250 yyextra->current->args = "(";
2251 yyextra->currentArgumentContext = FuncQual;
2252 yyextra->fullArgString = yyextra->current->args;
2253 yyextra->copyArgString = &yyextra->current->args;
2254 //printf("Found %s\n",qPrint(yyextra->current->name));
2255 BEGIN( ReadFuncArgType ) ;
2256 }
2257 else
2258 {
2259 yyextra->current->name+="(";
2260 yyextra->roundCount++;
2261 }
2262 }
2263<EndTemplate>">"{BNopt}/"("({BN}*{TSCOPE}{BN}*"::")*({BN}*"*"{BN}*)+ { // function pointer returning a template instance
2264 lineCount(yyscanner);
2265 yyextra->current->name+='>';
2266 if (yyextra->roundCount==0 && --yyextra->sharpCount<=0)
2267 {
2268 BEGIN(FindMembers);
2269 }
2270 }
2271<EndTemplate>">"{BNopt}/"::" {
2272 lineCount(yyscanner);
2273 yyextra->current->name+='>';
2274 // *yyextra->currentTemplateSpec+='>';
2275 if (yyextra->roundCount==0 && --yyextra->sharpCount<=0)
2276 {
2277 BEGIN(FindMemberName);
2278 }
2279 }
2280<ClassTemplSpec,EndTemplate>"(" { yyextra->current->name+=*yytext;
2281 yyextra->roundCount++;
2282 }
2283<ClassTemplSpec,EndTemplate>")" { yyextra->current->name+=*yytext;
2284 if (yyextra->roundCount>0) yyextra->roundCount--;
2285 }
2286<EndTemplate>. {
2287 yyextra->current->name+=*yytext;
2288 // *yyextra->currentTemplateSpec+=*yytext;
2289 }
2290<FindMembers>"define"{BN}*"("{BN}*["'] {
2291 if (yyextra->insidePHP)
2292 {
2293 yyextra->current->bodyLine = yyextra->yyLineNr;
2294 yyextra->current->bodyColumn = yyextra->yyColNr;
2295 BEGIN( DefinePHP );
2296 }
2297 else
2298 REJECT;
2299 }
2300<CopyHereDoc>{ID} { // PHP heredoc
2301 yyextra->delimiter = yytext;
2302 *yyextra->pCopyHereDocGString << yytext;
2303 BEGIN(CopyHereDocEnd);
2304 }
2305<CopyHereDoc>"\""{ID}/"\"" { // PHP quoted heredoc
2306 yyextra->delimiter = &yytext[1];
2307 *yyextra->pCopyHereDocGString << yytext;
2308 BEGIN(CopyHereDocEnd);
2309 }
2310<CopyHereDoc>"'"{ID}/"'" { // PHP nowdoc
2311 yyextra->delimiter = &yytext[1];
2312 *yyextra->pCopyHereDocGString << yytext;
2313 BEGIN(CopyHereDocEnd);
2314 }
2315<HereDoc>{ID} { // PHP heredoc
2316 yyextra->delimiter = yytext;
2317 BEGIN(HereDocEnd);
2318 }
2319<HereDoc>"\""{ID}/"\"" { // PHP quoted heredoc
2320 yyextra->delimiter = &yytext[1];
2321 BEGIN(HereDocEnd);
2322 }
2323<HereDoc>"'"{ID}/"'" { // PHP nowdoc
2324 yyextra->delimiter = &yytext[1];
2325 BEGIN(HereDocEnd);
2326 }
2327<HereDocEnd>^{Bopt}{ID} { // id at start of the line could mark the end of the block
2328 if (yyextra->delimiter==DString(yytext).stripWhiteSpace()) // it is the end marker
2329 {
2330 BEGIN(yyextra->lastHereDocContext);
2331 }
2332 }
2333<HereDocEnd>. { }
2334<CopyHereDocEnd>^{Bopt}{ID} { // id at start of the line could mark the end of the block
2335 *yyextra->pCopyHereDocGString << yytext;
2336 if (yyextra->delimiter==DString(yytext).stripWhiteSpace()) // it is the end marker
2337 {
2338 BEGIN(yyextra->lastHereDocContext);
2339 }
2340 }
2341<CopyHereDocEnd>\n {
2342 lineCount(yyscanner);
2343 *yyextra->pCopyHereDocGString << yytext;
2344 }
2345<CopyHereDocEnd>{ID} {
2346 *yyextra->pCopyHereDocGString << yytext;
2347 }
2348<CopyHereDocEnd>. {
2349 *yyextra->pCopyHereDocGString << yytext;
2350 }
2351<FindMembers>"Q_OBJECT"|"Q_GADGET" { // Qt object / gadget macro
2352 }
2353<FindMembers>"Q_PROPERTY" { // Qt property declaration
2354 yyextra->yyBegLineNr = yyextra->yyLineNr;
2355 yyextra->yyBegColNr = yyextra->yyColNr;
2356 yyextra->current->protection = Protection::Public ; // see bug734245 & bug735462
2357 yyextra->current->mtype = yyextra->mtype = MethodTypes::Property;
2358 yyextra->current->type.clear();
2359 BEGIN(QtPropType);
2360 }
2361<QtPropType>"(" { // start of property arguments
2362 }
2363<QtPropAttr>")" { // end of property arguments
2364 unput(';');
2365 BEGIN(FindMembers);
2366 }
2367<QtPropType>{BN}+ {
2368 yyextra->current->name+=yytext;
2369 }
2370<QtPropType>"*" {
2371 yyextra->current->type+= yyextra->current->name;
2372 yyextra->current->type+= yytext;
2373 yyextra->current->name="";
2374 }
2375<QtPropType>({TSCOPE}"::")*{TSCOPE} {
2376 yyextra->current->type+= yyextra->current->name;
2377 yyextra->current->name=yytext;
2378 }
2379<QtPropType,QtPropAttr>{BN}+"READ"{BN}+ {
2380 yyextra->current->spec.setReadable(true);
2381 BEGIN(QtPropRead);
2382 }
2383<QtPropType,QtPropAttr>{BN}+"WRITE"{BN}+ {
2384 yyextra->current->spec.setWritable(true);
2385 BEGIN(QtPropWrite);
2386 }
2387<QtPropType,QtPropAttr>{BN}+"MEMBER"{BN}+{ID} | // member property => not supported yet
2388<QtPropType,QtPropAttr>{BN}+"RESET"{BN}+{ID} | // reset method => not supported yet
2389<QtPropType,QtPropAttr>{BN}+"SCRIPTABLE"{BN}+{ID} | // scriptable property => not supported yet
2390<QtPropType,QtPropAttr>{BN}+"DESIGNABLE"{BN}+{ID} | // designable property => not supported yet
2391<QtPropType,QtPropAttr>{BN}+"NOTIFY"{BN}+{ID} | // notify property => not supported yet
2392<QtPropType,QtPropAttr>{BN}+"REVISION"{BN}+{ID} | // revision property => not supported yet
2393<QtPropType,QtPropAttr>{BN}+"STORED"{BN}+{ID} | // stored property => not supported yet
2394<QtPropType,QtPropAttr>{BN}+"USER"{BN}+{ID} | // user property => not supported yet
2395<QtPropType,QtPropAttr>{BN}+"CONSTANT"{BN} | // constant property => not supported yet
2396<QtPropType,QtPropAttr>{BN}+"FINAL"{BN} { // final property => not supported yet
2397 BEGIN(QtPropAttr);
2398 }
2399<QtPropRead>{ID} {
2400 yyextra->current->read = yytext;
2401 BEGIN(QtPropAttr);
2402 }
2403<QtPropWrite>{ID} {
2404 yyextra->current->write = yytext;
2405 BEGIN(QtPropAttr);
2406 }
2407<FindMembers>"friend"{BN}+("class"|"union"|"struct"){BN}+ {
2408 yyextra->current->name=yytext;
2409 lineCount(yyscanner) ;
2410 BEGIN(FindMembers);
2411 }
2412<FindMembers>"requires" { // C++20 requires clause
2413 if (yyextra->insideJava) REJECT;
2414 yyextra->current->req.clear();
2415 yyextra->requiresContext = YY_START;
2416 BEGIN(RequiresClause);
2417 }
2418<RequiresClause>"requires"{BN}*/"{" { // requires requires { ... }
2419 if (yyextra->insideJava) REJECT;
2420 lineCount(yyscanner) ;
2421 yyextra->current->req+=yytext;
2422 BEGIN( RequiresExpression ) ;
2423 }
2424<RequiresClause>"requires"{BN}*"(" { // requires requires(T x) { ... }
2425 if (yyextra->insideJava) REJECT;
2426 lineCount(yyscanner) ;
2427 yyextra->current->req+=yytext;
2428 yyextra->lastRoundContext=RequiresExpression;
2429 yyextra->pCopyRoundString=&yyextra->current->req;
2430 yyextra->roundCount=0;
2431 BEGIN( CopyRound ) ;
2432 }
2433<RequiresExpression>"{" {
2434 yyextra->current->req+=yytext;
2435 yyextra->lastCurlyContext=RequiresClause;
2436 yyextra->pCopyCurlyString=&yyextra->current->req;
2437 yyextra->curlyCount=0;
2438 BEGIN( CopyCurly ) ;
2439 }
2440<RequiresExpression>\n {
2441 yyextra->current->req+=' ';
2442 lineCount(yyscanner);
2443 }
2444<RequiresExpression>. {
2445 yyextra->current->req+=yytext;
2446 }
2447<RequiresClause>"(" { // requires "(A && B)"
2448 yyextra->current->req+=yytext;
2449 yyextra->lastRoundContext=RequiresClause;
2450 yyextra->pCopyRoundString=&yyextra->current->req;
2451 yyextra->roundCount=0;
2452 BEGIN( CopyRound ) ;
2453 }
2454<RequiresClause>{NOTopt}{SCOPENAME}{BNopt}"(" { // "requires func(x)"
2455 if (startOfRequiresExpression(yyextra->current->req))
2456 {
2457 lineCount(yyscanner);
2458 yyextra->current->req+=yytext;
2459 yyextra->lastRoundContext=RequiresClause;
2460 yyextra->pCopyRoundString=&yyextra->current->req;
2461 yyextra->roundCount=0;
2462 BEGIN( CopyRound );
2463 }
2464 else
2465 {
2466 REJECT;
2467 }
2468 }
2469<RequiresClause>{NOTopt}{SCOPENAME}{BNopt}"<" { // "requires C<S,T>"
2470 if (startOfRequiresExpression(yyextra->current->req))
2471 {
2472 lineCount(yyscanner);
2473 yyextra->current->req+=yytext;
2474 yyextra->lastSharpContext=RequiresClause;
2475 yyextra->pCopySharpString=&yyextra->current->req;
2476 yyextra->sharpCount=0;
2477 BEGIN( CopySharp );
2478 }
2479 else
2480 {
2481 REJECT
2482 }
2483 }
2484<RequiresClause>{NOTopt}{SCOPENAME} { // something like "requires true" or "requires !my::value"
2485 if (startOfRequiresExpression(yyextra->current->req))
2486 {
2487 lineCount(yyscanner);
2488 yyextra->current->req=yytext;
2489 BEGIN(yyextra->requiresContext);
2490 }
2491 else
2492 {
2493 REJECT;
2494 }
2495 }
2496<RequiresClause>{NOTopt}"::"{ID} {
2497 lineCount(yyscanner);
2498 yyextra->current->req+=yytext;
2499 }
2500<RequiresClause>"||"|"&&"|"!"|("or"{BN}+)|("and"{BN}+)|("not"{BN}+) { // "requires A || B" or "requires A && B"
2501 lineCount(yyscanner);
2502 yyextra->current->req+=yytext;
2503 }
2504<RequiresClause>{BN}+ {
2505 yyextra->current->req+=' ';
2506 lineCount(yyscanner) ;
2507 }
2508<RequiresClause>. {
2509 unput(*yytext);
2510 yyextra->current->req=yyextra->current->req.simplifyWhiteSpace();
2511 BEGIN(yyextra->requiresContext);
2512 }
2513<FindMembers,FindMemberName>{SCOPENAME} {
2514 storeClangId(yyscanner,yytext);
2515 yyextra->yyBegColNr=yyextra->yyColNr;
2516 yyextra->yyBegLineNr=yyextra->yyLineNr;
2517 lineCount(yyscanner);
2518 if (yyextra->insideIDL && yyleng==9 && dstrcmp(yytext,"cpp_quote")==0)
2519 {
2520 BEGIN(CppQuote);
2521 }
2522 else if ((yyextra->insideIDL || yyextra->insideJava || yyextra->insideD) && yyleng==6 && dstrcmp(yytext,"import")==0)
2523 {
2524 if (yyextra->insideIDL)
2525 BEGIN(IDLImport);
2526 else // yyextra->insideJava or yyextra->insideD
2527 BEGIN(JavaImport);
2528 }
2529 else if (yyextra->insidePHP && dstrcmp(yytext,"use")==0)
2530 {
2531 BEGIN(PHPUse);
2532 }
2533 else if (yyextra->insideJava && dstrcmp(yytext,"package")==0)
2534 {
2535 lineCount(yyscanner);
2536 BEGIN(PackageName);
2537 }
2538 else if (yyextra->insideIDL && dstrcmp(yytext,"case")==0)
2539 {
2540 BEGIN(IDLUnionCase);
2541 }
2542 else if (yyextra->insideTryBlock && dstrcmp(yytext,"catch")==0)
2543 {
2544 yyextra->insideTryBlock=false;
2545 BEGIN(TryFunctionBlock);
2546 }
2547 else if (yyextra->insideCpp && dstrcmp(yytext,"alignas")==0)
2548 {
2549 yyextra->lastAlignAsContext = YY_START;
2550 BEGIN(AlignAs);
2551 }
2552 else if (yyextra->insideJS && dstrcmp(yytext,"var")==0)
2553 { // javascript variable
2554 yyextra->current->type="var";
2555 }
2556 else if (yyextra->insideJS && dstrcmp(yytext,"function")==0)
2557 { // javascript function
2558 yyextra->current->type="function";
2559 }
2560 else if (yyextra->insideCS && dstrcmp(yytext,"this")==0)
2561 {
2562 // C# indexer
2563 addType(yyscanner);
2564 yyextra->current->name="this";
2565 BEGIN(CSIndexer);
2566 }
2567 else if (yyextra->insideCpp && (dstrcmp(yytext,"static_assert")==0 || dstrcmp(yytext,"_Static_assert")==0))
2568 {
2569 // C/C++11 static_assert
2570 BEGIN(StaticAssert);
2571 }
2572 else if (yyextra->insideCpp && dstrcmp(yytext,"decltype")==0)
2573 {
2574 // C++11 decltype(x)
2575 addType(yyscanner);
2576 if (!yyextra->current->type.empty()) yyextra->current->type+=' ';
2577 yyextra->current->type+=yytext;
2578 BEGIN(DeclType);
2579 }
2580 else if (yyextra->insideSlice && dstrcmp(yytext,"optional")==0)
2581 {
2582 if (yyextra->current->type.empty())
2583 {
2584 yyextra->current->type = "optional";
2585 }
2586 else
2587 {
2588 yyextra->current->type += " optional";
2589 }
2590 yyextra->lastModifierContext = YY_START;
2591 BEGIN(SliceOptional);
2592 }
2593 else
2594 {
2595 if (YY_START==FindMembers)
2596 {
2597 addType(yyscanner);
2598 }
2599 bool javaLike = yyextra->insideJava || yyextra->insideCS || yyextra->insideD || yyextra->insidePHP || yyextra->insideJS;
2600 if (javaLike && dstrcmp(yytext,"public")==0)
2601 {
2602 yyextra->current->protection = Protection::Public;
2603 }
2604 else if (javaLike && dstrcmp(yytext,"protected")==0)
2605 {
2606 yyextra->current->protection = Protection::Protected;
2607 }
2608 else if ((yyextra->insideCS || yyextra->insideD || yyextra->insidePHP || yyextra->insideJS) && dstrcmp(yytext,"internal")==0)
2609 {
2610 yyextra->current->protection = Protection::Package;
2611 }
2612 else if (javaLike && dstrcmp(yytext,"private")==0)
2613 {
2614 yyextra->current->protection = Protection::Private;
2615 }
2616 else if (javaLike && dstrcmp(yytext,"static")==0)
2617 {
2618 if (YY_START==FindMembers)
2619 yyextra->current->name = yytext;
2620 else
2621 yyextra->current->name += yytext;
2622 yyextra->current->isStatic = true;
2623 }
2624 else
2625 {
2626 if (YY_START==FindMembers)
2627 yyextra->current->name = yytext;
2628 else
2629 yyextra->current->name += yytext;
2630 if (yyextra->current->name.startsWith("static "))
2631 {
2632 yyextra->current->isStatic = true;
2633 yyextra->current->name= yyextra->current->name.mid(7);
2634 }
2635 else if (yyextra->current->name.startsWith("inline "))
2636 {
2637 if (yyextra->current->type.empty())
2638 {
2639 yyextra->current->type="inline";
2640 }
2641 else
2642 {
2643 yyextra->current->type+="inline ";
2644 }
2645 yyextra->current->name= yyextra->current->name.mid(7);
2646 }
2647 else if (yyextra->current->name.startsWith("constexpr "))
2648 {
2649 if (yyextra->current->type.empty())
2650 {
2651 yyextra->current->type="constexpr";
2652 }
2653 else
2654 {
2655 yyextra->current->type+="constexpr ";
2656 }
2657 yyextra->current->name=yyextra->current->name.mid(10);
2658 }
2659 else if (yyextra->current->name.startsWith("consteval "))
2660 {
2661 if (yyextra->current->type.empty())
2662 {
2663 yyextra->current->type="consteval";
2664 }
2665 else
2666 {
2667 yyextra->current->type+="consteval ";
2668 }
2669 yyextra->current->name=yyextra->current->name.mid(10);
2670 }
2671 else if (yyextra->current->name.startsWith("constinit "))
2672 {
2673 if (yyextra->current->type.empty())
2674 {
2675 yyextra->current->type="constinit";
2676 }
2677 else
2678 {
2679 yyextra->current->type+="constinit ";
2680 }
2681 yyextra->current->name=yyextra->current->name.mid(10);
2682 }
2683 else if (yyextra->current->name.startsWith("const "))
2684 {
2685 if (yyextra->current->type.empty())
2686 {
2687 yyextra->current->type="const";
2688 }
2689 else
2690 {
2691 yyextra->current->type+="const ";
2692 }
2693 yyextra->current->name=yyextra->current->name.mid(6);
2694 }
2695 else if (yyextra->current->name.startsWith("volatile "))
2696 {
2697 if (yyextra->current->type.empty())
2698 {
2699 yyextra->current->type="volatile";
2700 }
2701 else
2702 {
2703 yyextra->current->type+="volatile ";
2704 }
2705 yyextra->current->name=yyextra->current->name.mid(9);
2706 }
2707 else if (yyextra->current->name.startsWith("typedef "))
2708 {
2709 if (yyextra->current->type.empty())
2710 {
2711 yyextra->current->type="typedef";
2712 }
2713 else
2714 {
2715 yyextra->current->type+="typedef ";
2716 }
2717 yyextra->current->name=yyextra->current->name.mid(8);
2718 }
2719 }
2720 DString tmp=yytext;
2721 if (nameIsOperator(tmp))
2722 {
2723 BEGIN( Operator );
2724 }
2725 else
2726 {
2727 yyextra->externLinkage=false; // see bug759247
2728 BEGIN(FindMembers);
2729 }
2730 }
2731 yyextra->current->name = yyextra->current->name.removeWhiteSpace();
2732 }
2733<StaticAssert>"(" {
2734 yyextra->lastSkipRoundContext = FindMembers;
2735 yyextra->roundCount=0;
2736 BEGIN(SkipRound);
2737 }
2738<StaticAssert>{BN}+ { lineCount(yyscanner); }
2739<StaticAssert>. { // variable with static_assert as name?
2740 unput(*yytext);
2741 BEGIN(FindMembers);
2742 }
2743<DeclType>"(" {
2744 yyextra->current->type+=yytext;
2745 yyextra->lastRoundContext=FindMembers;
2746 yyextra->pCopyRoundString=&yyextra->current->type;
2747 yyextra->roundCount=0;
2748 BEGIN(CopyRound);
2749 }
2750<DeclType>{BN}+ { lineCount(yyscanner); }
2751<DeclType>. {
2752 unput(*yytext);
2753 BEGIN(FindMembers);
2754 }
2755<CSIndexer>"["[^\n\‍]]*"]" {
2756 yyextra->current->name+=removeRedundantWhiteSpace(yytext);
2757 BEGIN(FindMembers);
2758 }
2759<FindMembers>[0-9]{ID} { // some number where we did not expect one
2760 }
2761<FindMembers>"." {
2762 if (yyextra->insideJava || yyextra->insideCS || yyextra->insideD)
2763 {
2764 yyextra->current->name+=".";
2765 }
2766 }
2767<FindMembers>"::" {
2768 yyextra->current->name+=yytext;
2769 }
2770<CppQuote>"("{B}*"\"" {
2771 yyextra->insideCppQuote=true;
2772 BEGIN(FindMembers);
2773 }
2774<IDLUnionCase>"::"
2775<IDLUnionCase>":" { BEGIN(FindMembers); }
2776<IDLUnionCase>\n { lineCount(yyscanner); }
2777<IDLUnionCase>.
2778<TryFunctionBlock>\n { lineCount(yyscanner); }
2779<TryFunctionBlock>"{" {
2780 yyextra->curlyCount=0;
2781 yyextra->lastCurlyContext = TryFunctionBlockEnd ;
2782 BEGIN( SkipCurly );
2783 }
2784<TryFunctionBlock>.
2785<TryFunctionBlockEnd>{BN}*"catch" { lineCount(yyscanner); BEGIN(TryFunctionBlock); // {BN}* added to fix bug 611193
2786 }
2787<TryFunctionBlockEnd>\n { unput(*yytext); // rule added to fix bug id 601138
2788 BEGIN( FindMembers );
2789 }
2790<TryFunctionBlockEnd>. { unput(*yytext);
2791 BEGIN( FindMembers );
2792 }
2793<EndCppQuote>")" {
2794 yyextra->insideCppQuote=false;
2795 BEGIN(FindMembers);
2796 }
2797<FindConceptParts>[^\/\n]* {
2798 yyextra->current->initializer << yytext;
2799 }
2800<FindConceptParts>. {
2801 yyextra->current->initializer << yytext;
2802 }
2803<FindConceptParts>\n {
2804 yyextra->current->initializer << yytext;
2805 yyextra->yyLineNr++;
2806 }
2807<FindConceptParts>{CCS} {
2808 yyextra->current->initializer << yytext;
2809 }
2810<FindConceptParts>{CPPC} {
2811 yyextra->current->initializer << yytext;
2812 }
2813<FindConceptParts>^[ \t]*{CCS}[!*] { // start of a special comment inside Concept definition
2814 DString text(yytext);
2815 size_t indent = text.find('/');
2816 //printf("## startLine=%d startColumn=%d\n",yyextra->current->startLine,indent);
2817 if (!yyextra->current->initializer.empty())
2818 {
2819 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
2820 initEntry(yyscanner);
2821 }
2822 yyextra->current->section = EntryType::makeConceptDocPart();
2823 yyextra->current->startLine = yyextra->yyLineNr;
2824 yyextra->current->startColumn = indent;
2825 yyextra->current->initializer.clear();
2826 BEGIN(FindConceptDocs);
2827 }
2828<FindConceptParts>^[ \t]*{CPPC}[!/].*\n {
2829 if (!yyextra->current->initializer.empty())
2830 {
2831 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
2832 initEntry(yyscanner);
2833 }
2834 DString line(yytext);
2835 size_t indent = line.find('/');
2836 yyextra->current->section = EntryType::makeConceptDocPart();
2837 yyextra->current->startLine = yyextra->yyLineNr;
2838 yyextra->current->startColumn = indent;
2839 yyextra->current->initializer.clear();
2840 yyextra->current->initializer << line.mid(indent+3);
2841 yyextra->yyLineNr++;
2842 BEGIN(FindConceptCxxDocs);
2843 }
2844<FindConceptCxxDocs>^[ \t]*{CPPC}.*\n {
2845 DString line(yytext);
2846 size_t p = line.find('/');
2847 if (line.at(p+2)=='!' || line.at(p+2)=='/') p++;
2848 yyextra->current->initializer << line.mid(p+2);
2849 yyextra->yyLineNr++;
2850 }
2851<FindConceptCxxDocs>{CCS}|{CCE}|{CPPC} {
2852 yyextra->current->initializer << yytext;
2853 }
2854<FindConceptCxxDocs>. {
2855 if (!yyextra->current->initializer.empty())
2856 {
2857 //printf("*** doc=[[%s]\n",qPrint(yyextra->current->initializer.str()));
2858 handleCommentBlock(yyscanner,yyextra->current->initializer.str(),false);
2859 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
2860 initEntry(yyscanner);
2861 }
2862 unput(*yytext);
2863 yyextra->current->section = EntryType::makeConceptCodePart();
2864 yyextra->current->startLine = yyextra->yyLineNr;
2865 BEGIN(FindConceptParts);
2866 }
static void handleCommentBlock(yyscan_t yyscanner, const DString &doc, bool brief)
2867<FindConceptDocs>^[ \t]*"*"+/[^/] { // skip leading indentation
2868 }
2869<FindConceptDocs>[^\*\n]+ {
2870 yyextra->current->initializer << yytext;
2871 }
2872<FindConceptDocs>\n {
2873 yyextra->current->initializer << yytext;
2874 yyextra->yyLineNr++;
2875 }
2876<FindConceptDocs>"*"*{CCE}[ t]*\n? {
2877 if (!yyextra->current->initializer.empty())
2878 {
2879 //printf("*** doc=[[%s]\n",qPrint(yyextra->current->initializer.str()));
2880 handleCommentBlock(yyscanner,yyextra->current->initializer.str(),false);
2881 yyextra->current->section = EntryType::makeConceptDocPart();
2882 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
2883 initEntry(yyscanner);
2884 }
2885 lineCount(yyscanner);
2886 yyextra->current->section = EntryType::makeConceptCodePart();
2887 yyextra->current->startLine = yyextra->yyLineNr;
2888 BEGIN(FindConceptParts);
2889 }
2890<FindConceptDocs>"*"*{CCE} {
2891 if (!yyextra->current->initializer.empty())
2892 {
2893 //printf("*** doc=[[%s]\n",qPrint(yyextra->current->initializer.str()));
2894 handleCommentBlock(yyscanner,yyextra->current->initializer.str(),false);
2895 yyextra->current->section = EntryType::makeConceptDocPart();
2896 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
2897 initEntry(yyscanner);
2898 }
2899 yyextra->current->section = EntryType::makeConceptCodePart();
2900 yyextra->current->startLine = yyextra->yyLineNr;
2901 BEGIN(FindConceptParts);
2902 }
2903<FindConceptParts><<EOF>> {
2904 if (!yyextra->current->initializer.empty())
2905 {
2906 if (!yyextra->current->section.isConceptCodePart())
2907 {
2908 yyextra->current->section = EntryType::makeConceptDocPart();
2909 }
2910 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
2911 initEntry(yyscanner);
2912 }
2913 yyterminate();
2914 }
#define yyterminate()
2915<FindMembers,FindFields>{B}*"#" { if (yyextra->insidePHP)
2916 REJECT;
2917 yyextra->lastCPPContext = YY_START;
2918 BEGIN( SkipCPP ) ;
2919 }
2920<FindMembers,FindFields>{B}*"#"{B}*"cmakedefine01" |
2921<FindMembers,FindFields>{B}*"#"{B}*("cmake")?"define" {
2922 if (yyextra->insidePHP)
2923 REJECT;
2924 yyextra->current->bodyLine = yyextra->yyLineNr;
2925 yyextra->current->bodyColumn = yyextra->yyColNr;
2926 yyextra->current->fileName = yyextra->fileName;
2927 yyextra->current->startLine = yyextra->yyLineNr;
2928 yyextra->current->startColumn = yyextra->yyColNr;
2929 yyextra->current->type.clear();
2930 yyextra->current->args = yyextra->current->args.simplifyWhiteSpace();
2931 yyextra->current->name = yyextra->current->name.stripWhiteSpace();
2932 yyextra->current->section = EntryType::makeDefine();
2933 yyextra->lastDefineContext = YY_START;
2934 BEGIN( SDefine );
2935 }
2936<FindMembers,ReadBody,ReadNSBody,ReadBodyIntf,SkipCurly,SkipCurlyCpp>{B}*"#"{B}+[0-9]+{B}+/"\"" { /* line control directive */
2937 yyextra->yyLineNr = atoi(&yytext[1]);
2938 //printf("setting line number to %d\n",yyextra->yyLineNr);
2939 yyextra->lastPreLineCtrlContext = YY_START;
2940 if (YY_START==ReadBody ||
2941 YY_START==ReadNSBody ||
2942 YY_START==ReadBodyIntf)
2943 {
2944 yyextra->current->program << yytext;
2945 }
2946 BEGIN( PreLineCtrl );
2947 }
2948<PreLineCtrl>"\""[^\n\"]*"\"" {
2949 yyextra->fileName = stripQuotes(yytext);
2950 if (yyextra->lastPreLineCtrlContext==ReadBody ||
2951 yyextra->lastPreLineCtrlContext==ReadNSBody ||
2952 yyextra->lastPreLineCtrlContext==ReadBodyIntf)
2953 {
2954 yyextra->current->program << yytext;
2955 }
2956 }
2957<PreLineCtrl>. {
2958 if (yyextra->lastPreLineCtrlContext==ReadBody ||
2959 yyextra->lastPreLineCtrlContext==ReadNSBody ||
2960 yyextra->lastPreLineCtrlContext==ReadBodyIntf)
2961 {
2962 yyextra->current->program << yytext;
2963 }
2964 }
2965<PreLineCtrl>\n {
2966 if (yyextra->lastPreLineCtrlContext==ReadBody ||
2967 yyextra->lastPreLineCtrlContext==ReadNSBody ||
2968 yyextra->lastPreLineCtrlContext==ReadBodyIntf)
2969 {
2970 yyextra->current->program << yytext;
2971 }
2972 lineCount(yyscanner);
2973 BEGIN( yyextra->lastPreLineCtrlContext );
2974 }
2975<SkipCPP>.
2976<SkipCPP>\\‍[\r]*"\n"[\r]* { lineCount(yyscanner); }
2977<SkipCPP>[\r]*\n[\r]* { lineCount(yyscanner);
2978 BEGIN( yyextra->lastCPPContext) ;
2979 }
2980<SDefine>{ID}{B}*"(" {
2981 yyextra->current->name = yytext;
2982 yyextra->current->name = yyextra->current->name.left(yyextra->current->name.length()-1).stripWhiteSpace();
2983 yyextra->current->args = "(";
2984 yyextra->current->bodyLine = yyextra->yyLineNr;
2985 yyextra->current->bodyColumn = yyextra->yyColNr;
2986 yyextra->currentArgumentContext = DefineEnd;
2987 yyextra->fullArgString=yyextra->current->args;
2988 yyextra->copyArgString=&yyextra->current->args;
2989 BEGIN( ReadFuncArgType ) ;
2990 }
2991 /*
2992<DefineArg>")" {
2993 //printf("Define with args\n");
2994 yyextra->current->args += ')';
2995 BEGIN( DefineEnd );
2996 }
2997<DefineArg>. {
2998 yyextra->current->args += *yytext;
2999 }
3000 */
3001<SDefine>{ID} {
3002 //printf("Define '%s' without args\n",yytext);
3003 storeClangId(yyscanner,yytext);
3004 yyextra->current->bodyLine = yyextra->yyLineNr;
3005 yyextra->current->bodyColumn = yyextra->yyColNr;
3006 yyextra->current->name = yytext;
3007 BEGIN(DefineEnd);
3008 }
3009<DefineEnd><<EOF>> |
3010<DefineEnd>\n {
3011 //printf("End define: doc=%s docFile=%s docLine=%d\n",qPrint(yyextra->current->doc),qPrint(yyextra->current->docFile),yyextra->current->docLine);
3012 lineCount(yyscanner);
3013 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
3014 initEntry(yyscanner);
3015 BEGIN(yyextra->lastDefineContext);
3016 }
3017<DefinePHPEnd>";" {
3018 //printf("End define\n");
3019 yyextra->current->fileName = yyextra->fileName;
3020 yyextra->current->startLine = yyextra->yyLineNr;
3021 yyextra->current->startColumn = yyextra->yyColNr;
3022 yyextra->current->type.clear();
3023 yyextra->current->type = "const";
3024 DString init = yyextra->current->initializer.str();
3025 init = init.simplifyWhiteSpace();
3026 init = init.left(init.length()-1);
3027 yyextra->current->initializer.str(init.str());
3028 yyextra->current->name = yyextra->current->name.stripWhiteSpace();
3029 yyextra->current->section = EntryType::makeVariable();
3030 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
3031 initEntry(yyscanner);
3032 BEGIN(FindMembers);
3033 }
3034<DefinePHPEnd>.
3035<DefineEnd>\\‍[\r]?\n {
3036 lineCount(yyscanner);
3037 yyextra->current->endBodyLine = yyextra->yyLineNr;
3038 }
3039<DefineEnd>\" {
3040 if (yyextra->insideIDL && yyextra->insideCppQuote)
3041 {
3042 BEGIN(EndCppQuote);
3043 }
3044 else
3045 {
3046 yyextra->lastStringContext=DefineEnd;
3047 BEGIN(SkipString);
3048 }
3049 }
3050<DefineEnd>.
3051<DefinePHP>{ID}["']{BN}*","{BN}* {
3052 yyextra->current->name = yytext;
3053 yyextra->current->name = yyextra->current->name.stripWhiteSpace();
3054 yyextra->current->name = yyextra->current->name.left(yyextra->current->name.length()-1).stripWhiteSpace();
3055 yyextra->current->name = yyextra->current->name.left(yyextra->current->name.length()-1);
3056 yyextra->current->bodyLine = yyextra->yyLineNr;
3057 yyextra->current->bodyColumn = yyextra->yyColNr;
3058 yyextra->lastRoundContext = DefinePHPEnd;
3059 yyextra->pCopyRoundGString = &yyextra->current->initializer;
3060 yyextra->roundCount = 0;
3061 BEGIN( GCopyRound );
3062 }
3063
3064<FindMembers>[\^%] { // ^ and % are C++/CLI extensions
3065 if (yyextra->insideCli)
3066 {
3067 addType(yyscanner);
3068 yyextra->current->name = yytext ;
3069 }
3070 else
3071 {
3072 REJECT;
3073 }
3074 }
3075<FindMembers>[*&]+ {
3076 yyextra->current->name += yytext ;
3077 addType(yyscanner);
3078 }
3079<FindMembers,MemberSpec,SFunction,NextSemi,EnumBaseType,BitFields,ReadInitializer,ReadInitializerPtr,OldStyleArgs,DefinePHPEnd>";"{BN}*{DCOMM}"<" {
3080 if (YY_START==ReadInitializer && yyextra->keepComment)
3081 {
3082 REJECT;
3083 }
3084 else
3085 {
3086 if (yyextra->current->bodyLine==-1)
3087 {
3088 yyextra->current->bodyLine=yyextra->yyLineNr;
3089 yyextra->current->bodyColumn = yyextra->yyColNr;
3090 }
3091 yyextra->docBlockContext = YY_START;
3092 yyextra->docBlockInBody = false;
3093 yyextra->docBlockAutoBrief = ( yytext[yyleng-2]=='*' && Config_getBool(JAVADOC_AUTOBRIEF) ) ||
3094 ( yytext[yyleng-2]=='!' && Config_getBool(QT_AUTOBRIEF) );
3095 if (YY_START==MemberSpec && yyextra->memspecEntry && yyextra->memspecEntry->briefFile.empty()) // see issue #10900
3096 {
3097 if (yytext[yyleng-3]=='/')
3098 {
3099 yyextra->memspecEntry->briefFile = yyextra->fileName;
3100 yyextra->memspecEntry->briefLine = yyextra->yyLineNr;
3101 }
3102 else
3103 {
3104 yyextra->memspecEntry->docFile = yyextra->fileName;
3105 yyextra->memspecEntry->docLine = yyextra->yyLineNr;
3106 }
3107 }
3108
3109 DString indent;
3110 indent.fill(' ',computeIndent(yytext,yyextra->column));
3111 yyextra->docBlock.str(indent.str());
3112 //printf("indent=%d\n",computeIndent(yytext+1,yyextra->column));
3113 lineCount(yyscanner);
3114
3115 yyextra->docBlockTerm = ';';
3116 if (YY_START==EnumBaseType && yyextra->current->section.isEnum())
3117 {
3118 yyextra->current->bitfields = ":"+yyextra->current->args;
3119 yyextra->current->args.clear();
3120 yyextra->current->section = EntryType::makeVariable();
3121 }
3122 if (yytext[yyleng-3]=='/')
3123 {
3124 startCommentBlock(yyscanner,true);
3125 BEGIN( DocLine );
3126 }
3127 else
3128 {
3129 startCommentBlock(yyscanner,false);
3130 BEGIN( DocBlock );
3131 }
3132 }
3133 }
DString fill(char c, size_t len)
Fills a string with a predefined character.
Definition dstring.h:282
static int computeIndent(const char *s)
#define Config_getBool(name)
Definition config.h:33
static void startCommentBlock(yyscan_t yyscanner, bool)
3134<MemberSpec,FindFields,FindMembers,NextSemi,EnumBaseType,BitFields,ReadInitializer,ReadInitializerPtr,OldStyleArgs>","{BN}*{DCOMM}"<" {
3135 if (YY_START==ReadInitializer && yyextra->keepComment)
3136 {
3137 REJECT;
3138 }
3139 else
3140 {
3141 yyextra->docBlockContext = YY_START;
3142 yyextra->docBlockInBody = false;
3143 yyextra->docBlockAutoBrief = ( yytext[yyleng-2]=='*' && Config_getBool(JAVADOC_AUTOBRIEF) ) ||
3144 ( yytext[yyleng-2]=='!' && Config_getBool(QT_AUTOBRIEF) );
3145
3146 DString indent;
3147 indent.fill(' ',computeIndent(yytext,yyextra->column));
3148 yyextra->docBlock.str(indent.str());
3149 lineCount(yyscanner);
3150
3151 yyextra->docBlockTerm = ',';
3152 if (YY_START==EnumBaseType && yyextra->current->section.isEnum())
3153 {
3154 yyextra->current->bitfields = ":"+yyextra->current->args;
3155 yyextra->current->args.clear();
3156 yyextra->current->section = EntryType::makeVariable();
3157 }
3158 if (yytext[yyleng-3]=='/')
3159 {
3160 startCommentBlock(yyscanner,true);
3161 BEGIN( DocLine );
3162 }
3163 else
3164 {
3165 startCommentBlock(yyscanner,false);
3166 BEGIN( DocBlock );
3167 }
3168 }
3169 }
3170<DefineEnd,FindFields,ReadInitializer,ReadInitializerPtr,OldStyleArgs>{BN}*{DCOMM}"<" {
3171 if (YY_START==ReadInitializer && yyextra->keepComment)
3172 {
3173 REJECT;
3174 }
3175 else
3176 {
3177 if (yyextra->current->bodyLine==-1)
3178 {
3179 yyextra->current->bodyLine=yyextra->yyLineNr;
3180 yyextra->current->bodyColumn = yyextra->yyColNr;
3181 }
3182 yyextra->docBlockContext = YY_START;
3183 yyextra->docBlockInBody = false;
3184 yyextra->docBlockAutoBrief = ( yytext[yyleng-2]=='*' && Config_getBool(JAVADOC_AUTOBRIEF) ) ||
3185 ( yytext[yyleng-2]=='!' && Config_getBool(QT_AUTOBRIEF) );
3186 DString indent;
3187 indent.fill(' ',computeIndent(yytext,yyextra->column));
3188 yyextra->docBlock.str(indent.str());
3189 lineCount(yyscanner);
3190
3191 yyextra->docBlockTerm = 0;
3192 if (yytext[yyleng-3]=='/')
3193 {
3194 startCommentBlock(yyscanner,true);
3195 BEGIN( DocLine );
3196 }
3197 else
3198 {
3199 startCommentBlock(yyscanner,false);
3200 BEGIN( DocBlock );
3201 }
3202 }
3203 }
3204
3205<FindMembers,FindFields>({CPPC}([!/]){B}*{CMD}"{")|({CCS}([!*]){B}*{CMD}"{") {
3206 //handleGroupStartCommand(yyextra->current->name);
3207 if (yyextra->previous && yyextra->previous->section.isGroupDoc())
3208 {
3209 // link open command to the group defined in the yyextra->previous entry
3210 yyextra->commentScanner.open(yyextra->previous.get(),yyextra->fileName,yyextra->yyLineNr);
3211 }
3212 else
3213 {
3214 // link open command to the yyextra->current entry
3215 yyextra->commentScanner.open(yyextra->current.get(),yyextra->fileName,yyextra->yyLineNr);
3216 }
3217 //yyextra->current = tmp;
3218 initEntry(yyscanner);
3219 if (yytext[1]=='/')
3220 {
3221 if (yytext[2]=='!' || yytext[2]=='/')
3222 {
3223 yyextra->docBlockContext = YY_START;
3224 yyextra->docBlockInBody = false;
3225 yyextra->docBlockAutoBrief = false;
3226 yyextra->docBlock.str(std::string());
3227 yyextra->docBlockTerm = 0;
3228 startCommentBlock(yyscanner,true);
3229 BEGIN(DocLine);
3230 }
3231 else
3232 {
3233 yyextra->lastCContext=YY_START;
3234 BEGIN(SkipCxxComment);
3235 }
3236 }
3237 else
3238 {
3239 if (yytext[2]=='!' || yytext[2]=='*')
3240 {
3241 yyextra->docBlockContext = YY_START;
3242 yyextra->docBlockInBody = false;
3243 yyextra->docBlock.str(std::string());
3244 yyextra->docBlockAutoBrief = ( yytext[yyleng-2]=='*' && Config_getBool(JAVADOC_AUTOBRIEF) ) ||
3245 ( yytext[yyleng-2]=='!' && Config_getBool(QT_AUTOBRIEF) );
3246 yyextra->docBlockTerm = 0;
3247 startCommentBlock(yyscanner,false);
3248 BEGIN(DocBlock);
3249 }
3250 else
3251 {
3252 yyextra->lastCContext=YY_START;
3253 BEGIN(SkipComment);
3254 }
3255 }
3256 }
3257<FindMembers,FindFields,ReadInitializer,ReadInitializerPtr>{CPPC}([!/]){B}*{CMD}"}".*|{CCS}([!*]){B}*{CMD}"}"[^*]*{CCE} {
3258 bool insideEnum = YY_START==FindFields || ((YY_START==ReadInitializer || YY_START==ReadInitializerPtr) && yyextra->lastInitializerContext==FindFields); // see bug746226
3259 yyextra->commentScanner.close(yyextra->current.get(),yyextra->fileName,yyextra->yyLineNr,insideEnum);
3260 lineCount(yyscanner);
3261 }
3262<FindMembers>"=>" {
3263 if (!yyextra->insideCS) REJECT;
3264 yyextra->current->bodyLine = yyextra->yyLineNr;
3265 yyextra->current->bodyColumn = yyextra->yyColNr;
3266 yyextra->current->initializer.str(yytext);
3267 yyextra->lastInitializerContext = YY_START;
3268 yyextra->sharpCount=0;
3269 yyextra->initBracketCount=0;
3270 yyextra->current->mtype = yyextra->mtype = MethodTypes::Property;
3271 yyextra->current->spec.setGettable(true);
3272 BEGIN(ReadInitializerPtr);
3273 }
3274<FindMembers>"=" { // in PHP code this could also be due to "<?="
3275 yyextra->current->bodyLine = yyextra->yyLineNr;
3276 yyextra->current->bodyColumn = yyextra->yyColNr;
3277 yyextra->current->initializer.str(" ");
3278 for (size_t ii = 2 ; ii < yyextra->yyColNr; ii++)
3279 yyextra->current->initializer << " ";
3280 yyextra->current->initializer << "=";
3281 yyextra->lastInitializerContext = YY_START;
3282 yyextra->sharpCount=0;
3283 yyextra->initBracketCount=0;
3284 BEGIN(ReadInitializer);
3285 }
3286<UNOIDLAttributeBlock>{BN}*[gs]"et"{BN}+"raises"{BN}*"("{BN}*{SCOPENAME}{BN}*(","{BN}*{SCOPENAME}{BN}*)*")"{BN}*";" {
3287 lineCount(yyscanner);
3288 yyextra->current->exception += " ";
3289 yyextra->current->exception += removeRedundantWhiteSpace(yytext);
3290 }
3291<UNOIDLAttributeBlock>"}" {
3292 yyextra->current->exception += " }";
3293 BEGIN(FindMembers);
3294 }
3295 /* Read initializer rules */
3296<ReadInitializer,ReadInitializerPtr>"(" {
3297 yyextra->lastRoundContext=YY_START;
3298 yyextra->pCopyRoundGString=&yyextra->current->initializer;
3299 yyextra->roundCount=0;
3300 yyextra->current->initializer << *yytext;
3301 BEGIN(GCopyRound);
3302 }
3303<ReadInitializer,ReadInitializerPtr>"[" {
3304 if (!yyextra->insidePHP) REJECT;
3305 yyextra->lastSquareContext=YY_START;
3306 yyextra->pCopySquareGString=&yyextra->current->initializer;
3307 yyextra->squareCount=0;
3308 yyextra->current->initializer << *yytext;
3309 BEGIN(GCopySquare);
3310 }
3311<ReadInitializer,ReadInitializerPtr>"{" {
3312 yyextra->lastCurlyContext=YY_START;
3313 yyextra->pCopyCurlyGString=&yyextra->current->initializer;
3314 yyextra->curlyCount=0;
3315 yyextra->current->initializer << *yytext;
3316 BEGIN(GCopyCurly);
3317 }
3318<ReadInitializer,ReadInitializerPtr>[;,] {
3319 //printf(">> initializer '%s' <<\n",qPrint(yyextra->current->initializer));
3320 if (*yytext==';' && yyextra->current_root->spec.isEnum())
3321 {
3322 yyextra->current->fileName = yyextra->fileName;
3323 yyextra->current->startLine = yyextra->yyLineNr;
3324 yyextra->current->startColumn = yyextra->yyColNr;
3325 yyextra->current->args = yyextra->current->args.simplifyWhiteSpace();
3326 yyextra->current->name = yyextra->current->name.stripWhiteSpace();
3327 yyextra->current->section = EntryType::makeVariable();
3328 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
3329 initEntry(yyscanner);
3330 BEGIN(FindMembers);
3331 }
3332 else if (*yytext==';' || (yyextra->lastInitializerContext==FindFields && yyextra->initBracketCount==0)) // yyextra->initBracketCount==0 was added for bug 665778
3333 {
3334 unput(*yytext);
3335 if (YY_START == ReadInitializerPtr) yyextra->current->initializer.str(std::string());
3336 BEGIN(yyextra->lastInitializerContext);
3337 }
3338 else if (*yytext==',' && yyextra->initBracketCount==0) // for "int a=0,b=0"
3339 {
3340 unput(*yytext);
3341 if (YY_START == ReadInitializerPtr) yyextra->current->initializer.str(std::string());
3342 BEGIN(yyextra->lastInitializerContext);
3343 }
3344 else
3345 {
3346 yyextra->current->initializer << *yytext;
3347 }
3348 }
3349<ReadInitializer,ReadInitializerPtr>{RAWBEGIN} { // C++11 raw string
3350 if (!yyextra->insideCpp)
3351 {
3352 REJECT;
3353 }
3354 else
3355 {
3356 yyextra->current->initializer << yytext;
3357 yyextra->delimiter = extractBeginRawStringDelimiter(yytext);
3358 yyextra->lastRawStringContext = YY_START;
3359 yyextra->pCopyRawGString = &yyextra->current->initializer;
3360 BEGIN(RawGString);
3361 //printf("RawGString delimiter='%s'\n",qPrint(delimiter));
3362 }
3363 }
DString extractBeginRawStringDelimiter(const char *rawStart)
Definition util.cpp:5340
3364<ReadInitializer>{CPPC}.* {
3365 if (yyextra->keepComment)
3366 {
3367 yyextra->current->initializer << yytext;
3368 }
3369 else
3370 {
3371 REJECT;
3372 }
3373 }
3374<ReadInitializer>{CCS} {
3375 if (yyextra->keepComment)
3376 {
3377 yyextra->current->initializer << yytext;
3378 BEGIN(InitCopyComment);
3379 }
3380 else
3381 {
3382 REJECT;
3383 }
3384 }
3385<InitCopyComment>{CCE} {
3386 yyextra->current->initializer << yytext;
3387 BEGIN(ReadInitializer);
3388 }
3389<InitCopyComment>\n {
3390 lineCount(yyscanner);
3391 yyextra->current->initializer << yytext;
3392 }
3393<InitCopyComment>. {
3394 yyextra->current->initializer << yytext;
3395 }
3396<InitCopyComment><<EOF>> {
3397 warn(yyextra->fileName,yyextra->yyLineNr,
3398 "reached end of file while inside a C style comment block!");
3399 yyterminate();
3400 }
#define warn(file, line, fmt,...)
Definition message.h:97
3401<RawGString>{RAWEND} {
3402 if (extractEndRawStringDelimiter(yytext)==yyextra->delimiter)
3403 {
3404 *yyextra->pCopyRawGString << yytext;
3405 BEGIN(yyextra->lastRawStringContext);
3406 }
3407 else
3408 {
3409 REJECT;
3410 }
3411 }
DString extractEndRawStringDelimiter(const char *rawEnd)
Definition util.cpp:5348
3412<RawGString>[^)\n]+ {
3413 *yyextra->pCopyRawGString << yytext;
3414 }
3415<RawGString>. {
3416 *yyextra->pCopyRawGString << yytext;
3417 }
3418<RawGString>\n {
3419 *yyextra->pCopyRawGString << yytext;
3420 lineCount(yyscanner);
3421 }
3422<RawString>{RAWEND} {
3423 *yyextra->pCopyRawString+=yytext;
3424 yyextra->fullArgString+=yytext;
3425 if (extractEndRawStringDelimiter(yytext)==yyextra->delimiter)
3426 {
3427 BEGIN(yyextra->lastRawStringContext);
3428 }
3429 }
3430<RawString>[^)]+ {
3431 *yyextra->pCopyRawString += yytext;
3432 yyextra->fullArgString+=yytext;
3433 }
3434<RawString>. {
3435 *yyextra->pCopyRawString += yytext;
3436 yyextra->fullArgString+=yytext;
3437 }
3438<RawString>\n {
3439 *yyextra->pCopyRawString += yytext;
3440 yyextra->fullArgString+=yytext;
3441 lineCount(yyscanner);
3442 }
3443<ReadInitializer,ReadInitializerPtr>\" {
3444 if (yyextra->insideIDL && yyextra->insideCppQuote)
3445 {
3446 BEGIN(EndCppQuote);
3447 }
3448 else
3449 {
3450 yyextra->lastStringContext=YY_START;
3451 yyextra->current->initializer << yytext;
3452 yyextra->pCopyQuotedGString=&yyextra->current->initializer;
3453 yyextra->stopAtInvalidString=false;
3454 BEGIN(CopyGString);
3455 }
3456 }
3457<ReadInitializer,ReadInitializerPtr>"->" {
3458 yyextra->current->initializer << yytext;
3459 }
3460<ReadInitializer,ReadInitializerPtr>("<<"|"<=") {
3461 yyextra->current->initializer << yytext;
3462 }
3463<ReadInitializer,ReadInitializerPtr>(">>") {
3464 if (yyextra->initBracketCount<=yyextra->sharpCount && yyextra->sharpCount>=2)
3465 {
3466 // heuristic to detect '>>' in A<B<C>>::D as '> >', but not e.g. 'A>>B' or A<B<(C>>2)>::D>
3467 yyextra->initBracketCount-=2;
3468 yyextra->sharpCount-=2;
3469 }
3470 yyextra->current->initializer << yytext;
3471 }
3472<ReadInitializer,ReadInitializerPtr>(">=") {
3473 yyextra->current->initializer << yytext;
3474 }
3475<ReadInitializer,ReadInitializerPtr>[<\‍[{(] {
3476 yyextra->initBracketCount++;
3477 yyextra->sharpCount++;
3478 yyextra->current->initializer << *yytext;
3479 }
3480<ReadInitializer,ReadInitializerPtr>[>\‍]})] {
3481 yyextra->initBracketCount--;
3482 yyextra->sharpCount--;
3483 if (*yytext=='}')
3484 {
3485 yyextra->current->endBodyLine=yyextra->yyLineNr;
3486 }
3487 yyextra->current->initializer << *yytext;
3488 }
3489<ReadInitializer,ReadInitializerPtr>\' {
3490 if (yyextra->insidePHP)
3491 {
3492 yyextra->current->initializer << yytext;
3493 yyextra->pCopyQuotedGString = &yyextra->current->initializer;
3494 yyextra->lastStringContext=YY_START;
3495 BEGIN(CopyPHPGString);
3496 }
3497 else
3498 {
3499 yyextra->current->initializer << yytext;
3500 }
3501 }
3502<ReadInitializer,ReadInitializerPtr>{CHARLIT} {
3503 if (yyextra->insidePHP)
3504 {
3505 REJECT;
3506 }
3507 else
3508 {
3509 yyextra->current->initializer << yytext;
3510 }
3511 }
3512<ReadInitializer,ReadInitializerPtr>\n {
3513 yyextra->current->initializer << *yytext;
3514 lineCount(yyscanner);
3515 }
3516<ReadInitializer,ReadInitializerPtr>"@\"" {
3517 //printf("yyextra->insideCS=%d\n",yyextra->insideCS);
3518 yyextra->current->initializer << yytext;
3519 if (!yyextra->insideCS && !yyextra->insideObjC)
3520 {
3521 REJECT;
3522 }
3523 else
3524 {
3525 // C#/ObjC verbatim string
3526 yyextra->lastSkipVerbStringContext=YY_START;
3527 yyextra->pSkipVerbString=&yyextra->current->initializer;
3528 BEGIN(SkipVerbString);
3529 }
3530 }
3531<SkipVerbString>[^\n"\\‍]+ {
3532 *yyextra->pSkipVerbString << yytext;
3533 }
3534<SkipVerbString>"\\\\" { // escaped backslash
3535 if (yyextra->insideCS) REJECT
3536 *yyextra->pSkipVerbString << yytext;
3537 }
3538<SkipVerbString>"\\\"" { // backslash escaped quote
3539 if (yyextra->insideCS) REJECT
3540 *yyextra->pSkipVerbString << yytext;
3541 }
3542<SkipVerbString>"\"\"" { // quote escape
3543 *yyextra->pSkipVerbString << yytext;
3544 }
3545<SkipVerbString>"\"" {
3546 *yyextra->pSkipVerbString << *yytext;
3547 BEGIN(yyextra->lastSkipVerbStringContext);
3548 }
3549<SkipVerbString>\n {
3550 *yyextra->pSkipVerbString << *yytext;
3551 lineCount(yyscanner);
3552 }
3553<SkipVerbString>. {
3554 *yyextra->pSkipVerbString << *yytext;
3555 }
3556<ReadInitializer,ReadInitializerPtr>"?>" {
3557 if (yyextra->insidePHP)
3558 BEGIN( FindMembersPHP );
3559 else
3560 yyextra->current->initializer << yytext;
3561 }
3562<ReadInitializer,ReadInitializerPtr>. {
3563 yyextra->current->initializer << *yytext;
3564 }
3565
3566 /* generic quoted string copy rules */
3567<CopyString,CopyPHPString>\\. {
3568 *yyextra->pCopyQuotedString+=yytext;
3569 }
3570<CopyString>\" {
3571 *yyextra->pCopyQuotedString+=*yytext;
3572 BEGIN( yyextra->lastStringContext );
3573 }
3574<CopyPHPString>\' {
3575 *yyextra->pCopyQuotedString+=*yytext;
3576 BEGIN( yyextra->lastStringContext );
3577 }
3578<CopyString,CopyPHPString>{CCS}|{CCE}|{CPPC} {
3579 *yyextra->pCopyQuotedString+=yytext;
3580 }
3581<CopyString,CopyPHPString>\n {
3582 *yyextra->pCopyQuotedString+=*yytext;
3583 lineCount(yyscanner);
3584 }
3585<CopyString,CopyPHPString>. {
3586 *yyextra->pCopyQuotedString+=*yytext;
3587 }
3588
3589 /* generic quoted growable string copy rules */
3590<CopyGString,CopyPHPGString>\\. {
3591 *yyextra->pCopyQuotedGString << yytext;
3592 }
3593<CopyGString>\" {
3594 *yyextra->pCopyQuotedGString << *yytext;
3595 BEGIN( yyextra->lastStringContext );
3596 }
3597<CopyPHPGString>\' {
3598 *yyextra->pCopyQuotedGString << *yytext;
3599 BEGIN( yyextra->lastStringContext );
3600 }
3601<CopyGString,CopyPHPGString>"<?php" { // we had an odd number of quotes.
3602 *yyextra->pCopyQuotedGString << yytext;
3603 BEGIN( yyextra->lastStringContext );
3604 }
3605<CopyGString,CopyPHPGString>{CCS}|{CCE}|{CPPC} {
3606 *yyextra->pCopyQuotedGString << yytext;
3607 }
3608<CopyGString,CopyPHPGString>\n {
3609 *yyextra->pCopyQuotedGString << *yytext;
3610 if (yyextra->stopAtInvalidString)
3611 {
3612 BEGIN( yyextra->lastStringContext );
3613 }
3614 else
3615 {
3616 lineCount(yyscanner);
3617 }
3618 }
3619<CopyGString,CopyPHPGString>. {
3620 *yyextra->pCopyQuotedGString << *yytext;
3621 }
3622
3623 /* generic C++ attribute copy rules */
3624<CopyC11Attribute>\" {
3625 *yyextra->pCopyC11AttributeString += *yytext;
3626 yyextra->pCopyQuotedString=yyextra->pCopyC11AttributeString;
3627 yyextra->lastStringContext=YY_START;
3628 BEGIN(CopyString);
3629 }
3630<CopyC11Attribute>\n {
3631 lineCount(yyscanner);
3632 *yyextra->pCopyC11AttributeString += *yytext;
3633 }
3634<CopyC11Attribute>{ID} {
3635 if (dstrcmp(yytext,"nodiscard")==0)
3636 {
3637 yyextra->current->spec.setNoDiscard(true);
3638 }
3639 *yyextra->pCopyC11AttributeString += yytext;
3640 }
3641<CopyC11Attribute>. {
3642 *yyextra->pCopyC11AttributeString += *yytext;
3643 }
3644<CopyC11Attribute>"]]" { /* end of the attribute list */
3645 yyextra->commentScanner.addDeprecatedDocs(yyextra->current.get(),
3646 yyextra->fileName,
3647 yyextra->yyLineNr,
3648 yyextra->thisParser);
3649 BEGIN(yyextra->lastC11AttributeContext);
3650 }
3651
3652
3653 /* generic round bracket list copy rules */
3654<CopyRound>\" {
3655 *yyextra->pCopyRoundString += *yytext;
3656 yyextra->pCopyQuotedString=yyextra->pCopyRoundString;
3657 yyextra->lastStringContext=YY_START;
3658 BEGIN(CopyString);
3659 }
3660<CopyRound>"(" {
3661 *yyextra->pCopyRoundString += *yytext;
3662 yyextra->roundCount++;
3663 }
3664<CopyRound>")" {
3665 *yyextra->pCopyRoundString += *yytext;
3666 if (--yyextra->roundCount<0)
3667 BEGIN(yyextra->lastRoundContext);
3668 }
3669<CopyRound>\n {
3670 lineCount(yyscanner);
3671 *yyextra->pCopyRoundString += *yytext;
3672 }
3673<CopyRound>\' {
3674 if (yyextra->insidePHP)
3675 {
3676 yyextra->current->initializer << yytext;
3677 yyextra->pCopyQuotedString = yyextra->pCopyRoundString;
3678 yyextra->lastStringContext=YY_START;
3679 BEGIN(CopyPHPString);
3680 }
3681 else
3682 {
3683 *yyextra->pCopyRoundString += yytext;
3684 }
3685 }
3686<CopyRound>{CHARLIT} {
3687 if (yyextra->insidePHP)
3688 {
3689 REJECT;
3690 }
3691 else
3692 {
3693 *yyextra->pCopyRoundString+=yytext;
3694 }
3695 }
3696<CopyRound>[^"'()\n,]+ {
3697 *yyextra->pCopyRoundString+=yytext;
3698 }
3699<CopyRound>. {
3700 *yyextra->pCopyRoundString+=*yytext;
3701 }
3702
3703 /* generic sharp bracket list copy rules */
3704<CopySharp>\" {
3705 *yyextra->pCopySharpString += *yytext;
3706 yyextra->pCopyQuotedString=yyextra->pCopySharpString;
3707 yyextra->lastStringContext=YY_START;
3708 BEGIN(CopyString);
3709 }
3710<CopySharp>"<" {
3711 *yyextra->pCopySharpString += *yytext;
3712 yyextra->sharpCount++;
3713 }
3714<CopySharp>">" {
3715 *yyextra->pCopySharpString += *yytext;
3716 if (--yyextra->sharpCount<0)
3717 {
3718 BEGIN(yyextra->lastSharpContext);
3719 }
3720 }
3721<CopySharp>\n {
3722 lineCount(yyscanner);
3723 *yyextra->pCopySharpString += *yytext;
3724 }
3725<CopySharp>\' {
3726 if (yyextra->insidePHP)
3727 {
3728 yyextra->current->initializer << yytext;
3729 yyextra->pCopyQuotedString = yyextra->pCopySharpString;
3730 yyextra->lastStringContext=YY_START;
3731 BEGIN(CopyPHPString);
3732 }
3733 else
3734 {
3735 *yyextra->pCopySharpString += yytext;
3736 }
3737 }
3738<CopySharp>{CHARLIT} {
3739 if (yyextra->insidePHP)
3740 {
3741 REJECT;
3742 }
3743 else
3744 {
3745 *yyextra->pCopySharpString+=yytext;
3746 }
3747 }
3748<CopySharp>[^"'<>\n,]+ {
3749 *yyextra->pCopySharpString+=yytext;
3750 }
3751<CopySharp>. {
3752 *yyextra->pCopySharpString+=*yytext;
3753 }
3754
3755
3756 /* generic round bracket list copy rules for growable strings */
3757<GCopyRound>\" {
3758 *yyextra->pCopyRoundGString << *yytext;
3759 yyextra->pCopyQuotedGString=yyextra->pCopyRoundGString;
3760 yyextra->lastStringContext=YY_START;
3761 BEGIN(CopyGString);
3762 }
3763<GCopyRound>"(" {
3764 *yyextra->pCopyRoundGString << *yytext;
3765 yyextra->roundCount++;
3766 }
3767<GCopyRound>")" {
3768 *yyextra->pCopyRoundGString << *yytext;
3769 if (--yyextra->roundCount<0)
3770 BEGIN(yyextra->lastRoundContext);
3771 }
3772<GCopyRound>\n {
3773 lineCount(yyscanner);
3774 *yyextra->pCopyRoundGString << *yytext;
3775 }
3776<GCopyRound>\' {
3777 if (yyextra->insidePHP)
3778 {
3779 yyextra->current->initializer << yytext;
3780 yyextra->pCopyQuotedGString = yyextra->pCopyRoundGString;
3781 yyextra->lastStringContext=YY_START;
3782 BEGIN(CopyPHPGString);
3783 }
3784 else
3785 {
3786 *yyextra->pCopyRoundGString << yytext;
3787 }
3788 }
3789<GCopyRound>{CHARLIT} {
3790 if (yyextra->insidePHP)
3791 {
3792 REJECT;
3793 }
3794 else
3795 {
3796 *yyextra->pCopyRoundGString << yytext;
3797 }
3798 }
3799<GCopyRound>"@\"" {
3800 if (!yyextra->insideCS) REJECT;
3801 *yyextra->pCopyRoundGString << yytext;
3802 yyextra->lastSkipVerbStringContext=YY_START;
3803 yyextra->pSkipVerbString=yyextra->pCopyRoundGString;
3804 BEGIN(SkipVerbString);
3805 }
3806<GCopyRound>[^"'()\n\/,R]+ { // R because of raw string start
3807 *yyextra->pCopyRoundGString << yytext;
3808 }
3809<GCopyRound>{RAWBEGIN} {
3810 *yyextra->pCopyRoundGString << yytext;
3811 yyextra->delimiter = extractBeginRawStringDelimiter(yytext);
3812 yyextra->lastRawStringContext = YY_START;
3813 yyextra->pCopyRawGString = yyextra->pCopyRoundGString;
3814 BEGIN(RawGString);
3815 }
3816<GCopyRound>. {
3817 *yyextra->pCopyRoundGString << *yytext;
3818 }
3819
3820 /* generic square bracket list copy rules for growable strings, we should only enter here in case of php, left the test part as in GCopyRound to keep it compatible with the round bracket version */
3821<GCopySquare>\" {
3822 *yyextra->pCopySquareGString << *yytext;
3823 yyextra->pCopyQuotedGString=yyextra->pCopySquareGString;
3824 yyextra->lastStringContext=YY_START;
3825 BEGIN(CopyGString);
3826 }
3827<GCopySquare>\' {
3828 *yyextra->pCopySquareGString << *yytext;
3829 if (yyextra->insidePHP)
3830 {
3831 yyextra->pCopyQuotedGString=yyextra->pCopySquareGString;
3832 yyextra->lastStringContext=YY_START;
3833 BEGIN(CopyPHPGString);
3834 }
3835 }
3836<GCopySquare>"[" {
3837 *yyextra->pCopySquareGString << *yytext;
3838 yyextra->squareCount++;
3839 }
3840<GCopySquare>"]" {
3841 *yyextra->pCopySquareGString << *yytext;
3842 if (--yyextra->squareCount<0)
3843 BEGIN(yyextra->lastSquareContext);
3844 }
3845<GCopySquare>\n {
3846 lineCount(yyscanner);
3847 *yyextra->pCopySquareGString << *yytext;
3848 }
3849<GCopySquare>\' {
3850 if (yyextra->insidePHP)
3851 {
3852 yyextra->current->initializer << yytext;
3853 yyextra->pCopyQuotedGString = yyextra->pCopySquareGString;
3854 yyextra->lastStringContext=YY_START;
3855 BEGIN(CopyPHPGString);
3856 }
3857 else
3858 {
3859 *yyextra->pCopySquareGString << yytext;
3860 }
3861 }
3862<GCopySquare>{CHARLIT} {
3863 if (yyextra->insidePHP)
3864 {
3865 REJECT;
3866 }
3867 else
3868 {
3869 *yyextra->pCopySquareGString << yytext;
3870 }
3871 }
3872<GCopySquare>[^"'\‍[\‍]\n\/,]+ {
3873 *yyextra->pCopySquareGString << yytext;
3874 }
3875<GCopySquare>. {
3876 *yyextra->pCopySquareGString << *yytext;
3877 }
3878
3879 /* generic curly bracket list copy rules */
3880<CopyCurly>\" {
3881 *yyextra->pCopyCurlyString += *yytext;
3882 yyextra->pCopyQuotedString=yyextra->pCopyCurlyString;
3883 yyextra->lastStringContext=YY_START;
3884 yyextra->keepComment=false;
3885 BEGIN(CopyString);
3886 }
3887<CopyCurly>\' {
3888 *yyextra->pCopyCurlyString += *yytext;
3889 if (yyextra->insidePHP)
3890 {
3891 yyextra->pCopyQuotedString=yyextra->pCopyCurlyString;
3892 yyextra->lastStringContext=YY_START;
3893 yyextra->keepComment=false;
3894 BEGIN(CopyPHPString);
3895 }
3896 }
3897<CopyCurly>"{" {
3898 *yyextra->pCopyCurlyString += *yytext;
3899 yyextra->curlyCount++;
3900 }
3901<CopyCurly>"}" {
3902 *yyextra->pCopyCurlyString += *yytext;
3903 if (--yyextra->curlyCount<0)
3904 {
3905 yyextra->keepComment=false;
3906 BEGIN(yyextra->lastCurlyContext);
3907 }
3908 }
3909<CopyCurly>{CHARLIT} { if (yyextra->insidePHP)
3910 {
3911 REJECT;
3912 }
3913 else
3914 {
3915 *yyextra->pCopyCurlyString += yytext;
3916 }
3917 }
3918<CopyCurly>[^"'{}\/\n,]+ {
3919 *yyextra->pCopyCurlyString += yytext;
3920 }
3921<CopyCurly>"/" { *yyextra->pCopyCurlyString += yytext; }
3922<CopyCurly>\n {
3923 lineCount(yyscanner);
3924 *yyextra->pCopyCurlyString += *yytext;
3925 }
3926<CopyCurly>. {
3927 *yyextra->pCopyCurlyString += *yytext;
3928 }
3929<CopyCurly>{CPPC}[^\n]* {
3930 if (yyextra->keepComment)
3931 {
3932 *yyextra->pCopyCurlyString += yytext;
3933 }
3934 else
3935 {
3936 REJECT;
3937 }
3938 }
3939<CopyCurly>{CCS} {
3940 if (yyextra->keepComment)
3941 {
3942 *yyextra->pCopyCurlyString += yytext;
3943 BEGIN(CopyComment);
3944 }
3945 else
3946 {
3947 REJECT;
3948 }
3949 }
3950<CopyComment>{CCE} {
3951 *yyextra->pCopyCurlyString += yytext;
3952 BEGIN(CopyCurly);
3953 }
3954<CopyComment>\n {
3955 lineCount(yyscanner);
3956 *yyextra->pCopyCurlyString += *yytext;
3957 }
3958<CopyComment>. {
3959 *yyextra->pCopyCurlyString += *yytext;
3960 }
3961<CopyComment><<EOF>> {
3962 warn(yyextra->fileName,yyextra->yyLineNr,
3963 "reached end of file while inside a C style comment block!");
3964 yyterminate();
3965 }
3966
3967 /* generic curly bracket list copy rules for growable strings */
3968<GCopyCurly>^"#"{B}+[0-9]+{B}+"\""[^\"\n]+"\""{B}+"1"{B}*\n? { // start of included file marker
3969 }
3970<GCopyCurly>^"#"{B}+[0-9]+{B}+"\""[^\"\n]+"\""{B}+"2"{B}*\n? { // end of included file marker
3971 DString line = yytext;
3972 size_t s = line.find(' ');
3973 if (s == DString::npos) s = line.find('\t');
3974 size_t e = line.find('"',s);
3975 yyextra->yyLineNr = line.mid(s,e-s).toInt();
3976 if (yytext[yyleng-1]=='\n')
3977 {
3978 lineCount(yyscanner);
3979 yyextra->column=0;
3980 }
3981 }
int toInt(bool *ok=nullptr, int base=10) const
Definition dstring.cpp:191
3982<GCopyCurly>\" {
3983 *yyextra->pCopyCurlyGString << *yytext;
3984 yyextra->pCopyQuotedGString=yyextra->pCopyCurlyGString;
3985 yyextra->lastStringContext=YY_START;
3986 yyextra->keepComment = false;
3987 BEGIN(CopyGString);
3988 }
3989<GCopyCurly>\' {
3990 *yyextra->pCopyCurlyGString << *yytext;
3991 if (yyextra->insidePHP)
3992 {
3993 yyextra->pCopyQuotedGString=yyextra->pCopyCurlyGString;
3994 yyextra->lastStringContext=YY_START;
3995 yyextra->keepComment = false;
3996 BEGIN(CopyPHPGString);
3997 }
3998 }
3999<GCopyCurly>"{" {
4000 *yyextra->pCopyCurlyGString << *yytext;
4001 yyextra->curlyCount++;
4002 }
4003<GCopyCurly>"}" {
4004 *yyextra->pCopyCurlyGString << *yytext;
4005 if (--yyextra->curlyCount<0)
4006 {
4007 yyextra->current->endBodyLine = yyextra->yyLineNr;
4008 yyextra->keepComment = false;
4009 BEGIN(yyextra->lastCurlyContext);
4010 }
4011 }
4012<GCopyCurly>{CHARLIT} { if (yyextra->insidePHP)
4013 {
4014 REJECT;
4015 }
4016 else
4017 {
4018 *yyextra->pCopyCurlyGString << yytext;
4019 }
4020 }
4021<GCopyCurly>[^"'{}\/\n,]+ {
4022 *yyextra->pCopyCurlyGString << yytext;
4023 }
4024<GCopyCurly>[,]+ {
4025 *yyextra->pCopyCurlyGString << yytext;
4026 }
4027<GCopyCurly>"/" { *yyextra->pCopyCurlyGString << yytext; }
4028<GCopyCurly>\n {
4029 lineCount(yyscanner);
4030 *yyextra->pCopyCurlyGString << *yytext;
4031 }
4032<GCopyCurly>. {
4033 *yyextra->pCopyCurlyGString << *yytext;
4034 }
4035<GCopyCurly>{CPPC}[^\n]* {
4036 if (yyextra->keepComment)
4037 {
4038 *yyextra->pCopyCurlyGString << yytext;
4039 }
4040 else
4041 {
4042 REJECT;
4043 }
4044 }
4045<GCopyCurly>{CCS} {
4046 if (yyextra->keepComment)
4047 {
4048 *yyextra->pCopyCurlyGString << yytext;
4049 BEGIN(GCopyComment);
4050 }
4051 else
4052 {
4053 REJECT;
4054 }
4055 }
4056<GCopyComment>{CCE} {
4057 *yyextra->pCopyCurlyGString << yytext;
4058 BEGIN(GCopyCurly);
4059 }
4060<GCopyComment>\n {
4061 lineCount(yyscanner);
4062 *yyextra->pCopyCurlyGString << *yytext;
4063 }
4064<GCopyComment>. {
4065 *yyextra->pCopyCurlyGString << *yytext;
4066 }
4067<GCopyComment><<EOF>> {
4068 warn(yyextra->fileName,yyextra->yyLineNr,
4069 "reached end of file while inside a C style comment block!");
4070 yyterminate();
4071 }
4072
4073 /* ---------------------- */
4074
4075
4076<FindMembers>":" {
4077 if (yyextra->current->type.empty() &&
4078 yyextra->current->name=="enum") // see bug 69041, C++11 style anon enum: 'enum : unsigned int {...}'
4079 {
4080 yyextra->current->section = EntryType::makeEnum();
4081 yyextra->current->name.clear();
4082 yyextra->current->args.clear();
4083 BEGIN(EnumBaseType);
4084 }
4085 else
4086 {
4087 if (yyextra->current->type.empty()) // anonymous padding field, e.g. "int :7;"
4088 {
4089 addType(yyscanner);
4090 yyextra->current->name.sprintf("__pad%d__",yyextra->padCount++);
4091 }
4092 BEGIN(BitFields);
4093 yyextra->current->bitfields+=":";
4094 }
4095 }
4096<BitFields>. {
4097 yyextra->current->bitfields+=*yytext;
4098 }
4099<EnumBaseType>. {
4100 yyextra->current->args+=*yytext;
4101 }
4102<EnumBaseType>\n {
4103 lineCount(yyscanner);
4104 yyextra->current->args+=' ';
4105 }
4106<FindMembers>[;,] {
4107 DString oldType = yyextra->current->type;
4108 if (yyextra->current->bodyLine==-1)
4109 {
4110 yyextra->current->bodyLine = yyextra->yyLineNr;
4111 yyextra->current->bodyColumn = yyextra->yyColNr;
4112 }
4113 if ( yyextra->insidePHP && yyextra->current->type.startsWith("var"))
4114 {
4115 yyextra->current->type = yyextra->current->type.mid(3);
4116 }
4117 if (yyextra->isTypedef && !yyextra->current->type.startsWith("typedef "))
4118 {
4119 yyextra->current->type.prepend("typedef ");
4120 }
4121 bool isStatic = yyextra->current->isStatic;
4122 Protection prot = yyextra->current->protection;
4123 bool isConcept = yyextra->current->section.isConcept();
4124 bool isModule = yyextra->current->section.isModuleDoc();
4125 if (isConcept) // C++20 concept
4126 {
4127 yyextra->current_root->moveToSubEntryAndRefresh( yyextra->current ) ;
4128 initEntry(yyscanner);
4129 }
4130 else if (isModule) // C++20 module
4131 {
4132 yyextra->current_root->moveToSubEntryAndRefresh( yyextra->current ) ;
4133 initEntry(yyscanner);
4134 }
4135 else if (!yyextra->current->name.empty() && !yyextra->current->section.isEnum())
4136 {
4137 yyextra->current->type=yyextra->current->type.simplifyWhiteSpace();
4138 yyextra->current->args=removeRedundantWhiteSpace(yyextra->current->args);
4139 yyextra->current->name=yyextra->current->name.stripWhiteSpace();
4140 if (yyextra->current->section.isClass()) // remove spec for "struct Bla bla;"
4141 {
4142 yyextra->current->spec = TypeSpecifier();
4143 }
4144 yyextra->current->section = EntryType::makeVariable() ;
4145 yyextra->current->fileName = yyextra->fileName;
4146 yyextra->current->startLine = yyextra->yyBegLineNr;
4147 yyextra->current->startColumn = yyextra->yyBegColNr;
4148 yyextra->current_root->moveToSubEntryAndRefresh( yyextra->current ) ;
4149 initEntry(yyscanner);
4150 }
4151 if ( *yytext == ',')
4152 {
4153 yyextra->current->isStatic = isStatic; // the static attribute holds for all variables
4154 yyextra->current->protection = prot;
4155 yyextra->current->name.clear();
4156 yyextra->current->args.clear();
4157 yyextra->current->brief.clear();
4158 yyextra->current->doc.clear();
4159 yyextra->current->initializer.str(std::string());
4160 yyextra->current->bitfields.clear();
4161 yyextra->current->type = stripFuncPtr(oldType);
4162 }
4163 else
4164 {
4165 yyextra->mtype = MethodTypes::Method;
4166 yyextra->virt = Specifier::Normal;
4167 yyextra->current->bodyLine = -1;
4168 yyextra->current->bodyColumn = 1;
4169 yyextra->current->groups.clear();
4170 initEntry(yyscanner);
4171 }
4172 }
4173
4174<FindMembers>"[" {
4175 if (yyextra->insideSlice)
4176 {
4177 yyextra->squareCount=1;
4178 yyextra->lastSquareContext = YY_START;
4179 yyextra->current->metaData += "[";
4180 BEGIN( SliceMetadata );
4181 }
4182 else if (!yyextra->insideCS &&
4183 (yyextra->current->name.empty() ||
4184 yyextra->current->name=="typedef"
4185 )
4186 ) // IDL function property
4187 {
4188 yyextra->squareCount=1;
4189 yyextra->lastSquareContext = YY_START;
4190 yyextra->idlAttr.clear();
4191 yyextra->idlProp.clear();
4192 yyextra->current->mtype = yyextra->mtype;
4193
4194 if (Config_getBool(IDL_PROPERTY_SUPPORT) &&
4195 yyextra->current->mtype == MethodTypes::Property)
4196 { // we are yyextra->inside the properties section of a dispinterface
4197 yyextra->odlProp = true;
4198 yyextra->current->spec.setGettable(true).setSettable(true);
4199 }
4200
4201 BEGIN( IDLAttribute );
4202 }
4203 else if (yyextra->insideCS &&
4204 yyextra->current->name.empty())
4205 {
4206 yyextra->squareCount=1;
4207 yyextra->lastSquareContext = YY_START;
4208 // Skip the C# attribute
4209 // for this member
4210 yyextra->current->args.clear();
4211 BEGIN( SkipSquare );
4212 }
4213 else
4214 {
4215 yyextra->current->args += yytext ;
4216 yyextra->squareCount=1;
4217 yyextra->externLinkage=false; // see bug759247
4218 BEGIN( Array ) ;
4219 }
4220 }
4221<SliceMetadata>"[" { // Global metadata.
4222 yyextra->squareCount++;
4223 yyextra->current->metaData += "[";
4224 }
4225<SliceMetadata>{BN}* {
4226 lineCount(yyscanner);
4227 }
4228<SliceMetadata>\"[^\"]*\" {
4229 yyextra->current->metaData += yytext;
4230 }
4231<SliceMetadata>"," {
4232 yyextra->current->metaData += yytext;
4233 }
4234<SliceMetadata>"]" {
4235 yyextra->current->metaData += yytext;
4236 if (--yyextra->squareCount<=0)
4237 {
4238 BEGIN (yyextra->lastSquareContext);
4239 }
4240 }
4241<SliceOptional>"(" {
4242 yyextra->current->type += "(";
4243 yyextra->roundCount++;
4244 }
4245<SliceOptional>[0-9]+ {
4246 yyextra->current->type += yytext;
4247 }
4248<SliceOptional>")" {
4249 yyextra->current->type += ")";
4250 if(--yyextra->roundCount<=0)
4251 {
4252 BEGIN (yyextra->lastModifierContext);
4253 }
4254 }
4255<IDLAttribute>"]" {
4256 // end of IDL function attribute
4257 if (--yyextra->squareCount<=0)
4258 {
4259 lineCount(yyscanner);
4260 if (yyextra->current->mtype == MethodTypes::Property)
4261 BEGIN( IDLPropName );
4262 else
4263 BEGIN( yyextra->lastSquareContext );
4264 }
4265 }
4266<IDLAttribute>"propput" {
4267 if (Config_getBool(IDL_PROPERTY_SUPPORT))
4268 {
4269 yyextra->current->mtype = MethodTypes::Property;
4270 }
4271 yyextra->current->spec.setSettable(true);
4272 }
4273<IDLAttribute>"propget" {
4274 if (Config_getBool(IDL_PROPERTY_SUPPORT))
4275 {
4276 yyextra->current->mtype = MethodTypes::Property;
4277 }
4278 yyextra->current->spec.setGettable(true);
4279 }
4280<IDLAttribute>"property" { // UNO IDL property
4281 yyextra->current->spec.setProperty(true);
4282 }
4283<IDLAttribute>"attribute" { // UNO IDL attribute
4284 yyextra->current->spec.setAttribute(true);
4285 }
4286<IDLAttribute>"optional" { // on UNO IDL interface/service/attribute/property
4287 yyextra->current->spec.setOptional(true);
4288 }
4289<IDLAttribute>"readonly" { // on UNO IDL attribute or property
4290 if (Config_getBool(IDL_PROPERTY_SUPPORT) && yyextra->odlProp)
4291 {
4292 yyextra->current->spec.setSettable(false);
4293 }
4294 else
4295 {
4296 yyextra->current->spec.setReadonly(true);
4297 }
4298 }
4299<IDLAttribute>"bound" { // on UNO IDL attribute or property
4300 yyextra->current->spec.setBound(true);
4301 }
4302<IDLAttribute>"removable" { // on UNO IDL property
4303 yyextra->current->spec.setRemovable(true);
4304 }
4305<IDLAttribute>"constrained" { // on UNO IDL property
4306 yyextra->current->spec.setConstrained(true);
4307 }
4308<IDLAttribute>"transient" { // on UNO IDL property
4309 yyextra->current->spec.setTransient(true);
4310 }
4311<IDLAttribute>"maybevoid" { // on UNO IDL property
4312 yyextra->current->spec.setMaybeVoid(true);
4313 }
4314<IDLAttribute>"maybedefault" { // on UNO IDL property
4315 yyextra->current->spec.setMaybeDefault(true);
4316 }
4317<IDLAttribute>"maybeambiguous" { // on UNO IDL property
4318 yyextra->current->spec.setMaybeAmbiguous(true);
4319 }
4320<IDLAttribute>. {
4321 }
4322<IDLPropName>{BN}*{ID}({BN}*[*]*{BN}*)? {
4323 // return type (probably HRESULT) - skip it
4324
4325 if (yyextra->odlProp)
4326 { // property type
4327 yyextra->idlProp = yytext;
4328 }
4329 }
4330<IDLPropName>{ID}{BN}*"(" {
4331 yyextra->current->name = yytext;
4332 yyextra->current->name = yyextra->current->name.left(yyextra->current->name.length()-1).stripWhiteSpace();
4333 yyextra->current->startLine = yyextra->yyLineNr;
4334 yyextra->current->startColumn = yyextra->yyColNr;
4335 BEGIN( IDLProp );
4336 }
4337<IDLPropName>{BN}*"("{BN}*{ID}{BN}*")"{BN}* {
4338 if (yyextra->odlProp)
4339 {
4340 yyextra->idlProp += yytext;
4341 }
4342 }
4343<IDLPropName>{ID}{BNopt}/";" {
4344 if (yyextra->odlProp)
4345 {
4346 yyextra->current->name = yytext;
4347 yyextra->idlProp = yyextra->idlProp.stripWhiteSpace();
4348 yyextra->odlProp = false;
4349
4350 BEGIN( IDLProp );
4351 }
4352 }
4353<IDLProp>{BN}*"["[^\‍]]*"]"{BN}* { // attribute of a parameter
4354 yyextra->idlAttr = yytext;
4355 yyextra->idlAttr=yyextra->idlAttr.stripWhiteSpace();
4356 }
4357<IDLProp>{ID} { // property type
4358 yyextra->idlProp = yytext;
4359 }
4360<IDLProp>{BN}*{ID}{BN}*"," { // Rare: Another parameter ([propput] HRESULT Item(int index, [in] Type theRealProperty);)
4361 if (yyextra->current->args.empty())
4362 yyextra->current->args = "(";
4363 else
4364 yyextra->current->args += ", ";
4365 yyextra->current->args += yyextra->idlAttr;
4366 yyextra->current->args += " ";
4367 yyextra->current->args += yyextra->idlProp; // prop was actually type of extra parameter
4368 yyextra->current->args += " ";
4369 yyextra->current->args += yytext;
4370 yyextra->current->args = yyextra->current->args.left(yyextra->current->args.length() - 1); // strip comma
4371 yyextra->idlProp.clear();
4372 yyextra->idlAttr.clear();
4373 BEGIN( IDLProp );
4374 }
4375<IDLProp>{BN}*{ID}{BN}*")"{BN}* {
4376 // the parameter name for the property - just skip.
4377 }
4378<IDLProp>";" {
4379 yyextra->current->fileName = yyextra->fileName;
4380 yyextra->current->type = yyextra->idlProp;
4381 yyextra->current->args = yyextra->current->args.simplifyWhiteSpace();
4382 if (!yyextra->current->args.empty())
4383 yyextra->current->args += ")";
4384 yyextra->current->name = yyextra->current->name.stripWhiteSpace();
4385 yyextra->current->section = EntryType::makeVariable();
4386 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
4387 initEntry(yyscanner);
4388 BEGIN( FindMembers );
4389 }
4390<IDLProp>. { // spaces, *, or other stuff
4391 //yyextra->idlProp+=yytext;
4392 }
4393<Array>"]" { yyextra->current->args += *yytext ;
4394 if (--yyextra->squareCount<=0)
4395 BEGIN( FindMembers ) ;
4396 }
4397<FuncFuncArray>"]" { yyextra->current->args += *yytext ;
4398 if (--yyextra->squareCount<=0)
4399 BEGIN( SFunction ) ;
4400 }
4401<Array,FuncFuncArray>"[" { yyextra->current->args += *yytext ;
4402 yyextra->squareCount++;
4403 }
4404<Array,FuncFuncArray>. { yyextra->current->args += *yytext ; }
4405<SkipSquare>"[" { yyextra->squareCount++; }
4406<SkipSquare>"]" {
4407 if (--yyextra->squareCount<=0)
4408 BEGIN( yyextra->lastSquareContext );
4409 }
4410<SkipSquare>\" {
4411 yyextra->lastStringContext=YY_START;
4412 BEGIN( SkipString );
4413 }
4414<SkipSquare>[^\n\‍[\‍]\"]+
4415<FindMembers>"<" { addType(yyscanner);
4416 yyextra->current->type += yytext ;
4417 BEGIN( Sharp ) ;
4418 }
4419<Sharp>">" { yyextra->current->type += *yytext ;
4420 if (--yyextra->sharpCount<=0)
4421 BEGIN( FindMembers ) ;
4422 }
4423<Sharp>"<" { yyextra->current->type += *yytext ;
4424 yyextra->sharpCount++;
4425 }
4426<Sharp>{BN}+ {
4427 yyextra->current->type += ' ';
4428 lineCount(yyscanner);
4429 }
4430<Sharp>. { yyextra->current->type += *yytext ; }
4431<FindFields>{ID} {
4432 storeClangId(yyscanner,yytext);
4433 yyextra->current->bodyLine = yyextra->yyLineNr;
4434 yyextra->current->bodyColumn = yyextra->yyColNr;
4435 yyextra->current->name = yytext;
4436 }
4437<FindFields>[({] {
4438 // Java enum initializer
4439 unput(*yytext);
4440 yyextra->lastInitializerContext = YY_START;
4441 yyextra->sharpCount=0;
4442 yyextra->initBracketCount=0;
4443 yyextra->current->initializer.str("=");
4444 BEGIN(ReadInitializer);
4445 }
4446<FindFields>"=" {
4447 yyextra->lastInitializerContext = YY_START;
4448 yyextra->sharpCount=0;
4449 yyextra->initBracketCount=0;
4450 yyextra->current->initializer.str(yytext);
4451 BEGIN(ReadInitializer);
4452 }
4453<FindFields>";" {
4454 if (yyextra->insideJava) // yyextra->last enum field in Java class
4455 {
4456 if (!yyextra->current->name.empty())
4457 {
4458 yyextra->current->fileName = yyextra->fileName;
4459 yyextra->current->startLine = yyextra->yyLineNr;
4460 yyextra->current->startColumn = yyextra->yyColNr;
4461 if (!yyextra->current_root->spec.isEnum())
4462 {
4463 yyextra->current->type = "@"; // enum marker
4464 }
4465 yyextra->current->args = yyextra->current->args.simplifyWhiteSpace();
4466 yyextra->current->name = yyextra->current->name.stripWhiteSpace();
4467 yyextra->current->section = EntryType::makeVariable();
4468 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
4469 initEntry(yyscanner);
4470 }
4471
4472 BEGIN( FindMembers );
4473 }
4474 else
4475 {
4476 REJECT;
4477 }
4478 }
4479<FindFields>"," {
4480 //printf("adding '%s' '%s' '%s' to enum '%s' (mGrpId=%d)\n",
4481 // qPrint(yyextra->current->type), qPrint(yyextra->current->name),
4482 // qPrint(yyextra->current->args), qPrint(yyextra->current_root->name),yyextra->current->mGrpId);
4483 if (!yyextra->current->name.empty())
4484 {
4485 yyextra->current->fileName = yyextra->fileName;
4486 if (yyextra->current_root->section.isEnum() || yyextra->current_root->spec.isEnum())
4487 {
4488 yyextra->current->startLine = yyextra->current->bodyLine;
4489 yyextra->current->startColumn = yyextra->current->bodyColumn;
4490 }
4491 else
4492 {
4493 yyextra->current->startLine = yyextra->yyLineNr;
4494 yyextra->current->startColumn = yyextra->yyColNr;
4495 }
4496 if (!yyextra->current_root->spec.isEnum())
4497 {
4498 yyextra->current->type = "@"; // enum marker
4499 }
4500 yyextra->current->args = yyextra->current->args.simplifyWhiteSpace();
4501 yyextra->current->name = yyextra->current->name.stripWhiteSpace();
4502 yyextra->current->section = EntryType::makeVariable();
4503 // add to the scope of the enum
4504 if (!yyextra->insideCS && !yyextra->insideJava &&
4505 !yyextra->current_root->spec.isStrong())
4506 // for C# and Java 1.5+ enum values always have to be explicitly qualified,
4507 // same for C++11 style enums (enum class Name {})
4508 {
4509 // add to the scope surrounding the enum (copy!)
4510 // we cannot add it directly as that would invalidate the iterator in parseCompounds.
4511 //printf("*** adding outer scope entry for %s\n",qPrint(yyextra->current->name));
4512 yyextra->outerScopeEntries.emplace_back(yyextra->current_root->parent(), std::make_shared<Entry>(*yyextra->current));
4513 }
4514 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
4515 initEntry(yyscanner);
4516 }
4517 else // probably a redundant ,
4518 {
4519 yyextra->current->reset();
4520 initEntry(yyscanner);
4521 }
4522 }
4523<FindFields>"[" { // attribute list in IDL
4524 yyextra->squareCount=1;
4525 yyextra->lastSquareContext = YY_START;
4526 BEGIN(SkipSquare);
4527 }
4528<ReadBody,ReadNSBody,ReadBodyIntf>[^\r\n\#{}"@'/<\\\$R]* { yyextra->current->program << yytext ; } // R because of raw string start
4529<ReadBody,ReadNSBody,ReadBodyIntf>{CPPC}.* { yyextra->current->program << yytext ; }
4530<ReadBody,ReadNSBody,ReadBodyIntf>"#".* { if (!yyextra->insidePHP)
4531 REJECT;
4532 // append PHP comment.
4533 yyextra->current->program << yytext ;
4534 }
4535 /* Interpolated string C# */
4536<SkipCurly,ReadBody,ReadNSBody,ReadBodyIntf,ReadExpressionBody,FindMembers,FindMemberName>$\" { if (!yyextra->insideCS) REJECT
4537 yyextra->current->program << yytext ;
4538 yyextra->pSkipInterpString = &yyextra->current->program;
4539 yyextra->lastSkipInterpStringContext=YY_START;
4540 yyextra->strCurlyCount = 0;
4541 BEGIN( SkipInterpString );
4542 }
4543<SkipInterpString>([^"\\{}\x000D\x000A\x0085\x2028\x2029]|"{{"|"}}"|"\\'"|"\\\""|"\\\\"|"\\0"|"\\a"|"\\b"|"\\f"|"\\n"|"\\r"|"\\t"|"\\v"|"\\x"{HEXDIGIT}{HEXDIGIT}?{HEXDIGIT}?{HEXDIGIT}?|"\\"[uU]{HEXDIGIT}{HEXDIGIT}{HEXDIGIT}{HEXDIGIT}{HEXDIGIT}{HEXDIGIT}{HEXDIGIT}{HEXDIGIT})* {
4544 *yyextra->pSkipInterpString << yytext;
4545 }
4546<SkipInterpString>"{" {
4547 *yyextra->pSkipInterpString << *yytext;
4548 yyextra->strCurlyCount++;
4549 }
4550<SkipInterpString>"}" {
4551 *yyextra->pSkipInterpString << *yytext;
4552 yyextra->strCurlyCount--;
4553 }
4554<SkipInterpString>\" {
4555 *yyextra->pSkipInterpString << *yytext;
4556 if (yyextra->strCurlyCount==0)
4557 {
4558 BEGIN( yyextra->lastSkipInterpStringContext );
4559 }
4560 }
4561<SkipInterpString>. {
4562 *yyextra->pSkipInterpString << *yytext;
4563 }
4564 /* Verbatim Interpolated string C# */
4565<SkipCurly,ReadBody,ReadNSBody,ReadBodyIntf,ReadExpressionBody,FindMembers,FindMemberName>$@\" { if (!yyextra->insideCS) REJECT
4566 yyextra->current->program << yytext ;
4567 yyextra->pSkipInterpVerbString = &yyextra->current->program;
4568 yyextra->lastSkipInterpVerbStringContext=YY_START;
4569 yyextra->strCurlyCount = 0;
4570 BEGIN( SkipInterpVerbString );
4571 }
4572<SkipInterpVerbString>([^\"{}]|"{{"|"}}"|"\"\"")* {
4573 *yyextra->pSkipInterpVerbString << yytext;
4574 }
4575<SkipInterpVerbString>"{" {
4576 *yyextra->pSkipInterpVerbString << *yytext;
4577 yyextra->strCurlyCount++;
4578 }
4579<SkipInterpVerbString>"}" {
4580 *yyextra->pSkipInterpVerbString << *yytext;
4581 yyextra->strCurlyCount--;
4582 }
4583<SkipInterpVerbString>\" {
4584 *yyextra->pSkipInterpVerbString << *yytext;
4585 if (yyextra->strCurlyCount==0)
4586 {
4587 BEGIN( yyextra->lastSkipInterpVerbStringContext );
4588 }
4589 }
4590<SkipInterpVerbString>. {
4591 *yyextra->pSkipInterpVerbString << *yytext;
4592 }
4593<ReadBody,ReadNSBody,ReadBodyIntf>"\$" { yyextra->current->program << yytext ; }
4594<ReadBody,ReadNSBody,ReadBodyIntf>@\" { yyextra->current->program << yytext ;
4595 yyextra->pSkipVerbString = &yyextra->current->program;
4596 yyextra->lastSkipVerbStringContext=YY_START;
4597 BEGIN( SkipVerbString );
4598 }
4599<ReadBody,ReadNSBody,ReadBodyIntf>"<<<" { if (yyextra->insidePHP)
4600 {
4601 yyextra->current->program << yytext ;
4602 yyextra->pCopyHereDocGString = &yyextra->current->program;
4603 yyextra->lastHereDocContext=YY_START;
4604 BEGIN( CopyHereDoc );
4605 }
4606 else
4607 {
4608 REJECT;
4609 }
4610 }
4611<ReadBody,ReadNSBody,ReadBodyIntf>{RAWBEGIN} {
4612 yyextra->current->program << yytext;
4613 yyextra->delimiter = extractBeginRawStringDelimiter(yytext);
4614 yyextra->lastRawStringContext = YY_START;
4615 yyextra->pCopyRawGString = &yyextra->current->program;
4616 BEGIN(RawGString);
4617 }
4618<ReadBody,ReadNSBody,ReadBodyIntf>\" { yyextra->current->program << yytext ;
4619 yyextra->pCopyQuotedGString = &yyextra->current->program;
4620 yyextra->lastStringContext=YY_START;
4621 yyextra->stopAtInvalidString=false;
4622 BEGIN( CopyGString );
4623 }
4624<ReadBody,ReadNSBody,ReadBodyIntf>{DCOMMC} { yyextra->doxygenComment=true; REJECT;}
4625<ReadBody,ReadNSBody,ReadBodyIntf>{CCS}{B}* { yyextra->current->program << yytext ;
4626 yyextra->lastContext = YY_START ;
4627 BEGIN( Comment ) ;
4628 }
4629<ReadBody,ReadNSBody,ReadBodyIntf>{CCS}{BL} { yyextra->current->program << yytext ;
4630 ++yyextra->yyLineNr ;
4631 yyextra->lastContext = YY_START ;
4632 BEGIN( Comment ) ;
4633 }
4634<ReadBody,ReadNSBody,ReadBodyIntf>"'" {
4635 if (!yyextra->insidePHP)
4636 {
4637 yyextra->current->program << yytext;
4638 }
4639 else
4640 { // begin of single quoted string
4641 yyextra->current->program << yytext;
4642 yyextra->pCopyQuotedGString = &yyextra->current->program;
4643 yyextra->lastStringContext=YY_START;
4644 BEGIN(CopyPHPGString);
4645 }
4646 }
4647<ReadBody,ReadNSBody,ReadBodyIntf>{CHARLIT} {
4648 if (yyextra->insidePHP)
4649 {
4650 REJECT; // for PHP code single quotes
4651 // are used for strings of arbitrary length
4652 }
4653 else
4654 {
4655 yyextra->current->program << yytext;
4656 }
4657 }
4658<ReadBody,ReadNSBody,ReadBodyIntf>"{" { yyextra->current->program << yytext ;
4659 ++yyextra->curlyCount ;
4660 }
4661<ReadBodyIntf>"}" {
4662 yyextra->current->program << yytext ;
4663 --yyextra->curlyCount ;
4664 }
4665<ReadBody,ReadNSBody>"}" {
4666 if ( yyextra->curlyCount>0 )
4667 {
4668 yyextra->current->program << yytext ;
4669 --yyextra->curlyCount ;
4670 }
4671 else
4672 {
4673 yyextra->current->endBodyLine = yyextra->yyLineNr;
4674 std::shared_ptr<Entry> original_root = yyextra->current_root; // save root this namespace is in
4675 if (yyextra->current->section.isNamespace() && yyextra->current->type == "namespace")
4676 {
4677 //printf("namespace %s\n",qPrint(yyextra->current->name));
4678 // save documentation values
4679 DString doc = yyextra->current->doc;
4680 int docLine = yyextra->current->docLine;
4681 DString docFile = yyextra->current->docFile;
4682 DString brief = yyextra->current->brief;
4683 int briefLine = yyextra->current->briefLine;
4684 DString briefFile = yyextra->current->briefFile;
4685 auto groups = yyextra->current->groups;
4686 auto anchors = yyextra->current->anchors;
4687 auto sli = yyextra->current->sli;
4688 auto rqli = yyextra->current->rqli;
4689 // reset documentation values
4690 yyextra->current->doc = "";
4691 yyextra->current->docLine = 0;
4692 yyextra->current->docFile = "";
4693 yyextra->current->brief = "";
4694 yyextra->current->briefLine = 0;
4695 yyextra->current->briefFile = "";
4696 yyextra->current->groups.clear();
4697 yyextra->current->anchors.clear();
4698 yyextra->current->sli.clear();
4699 yyextra->current->rqli.clear();
4700 size_t split_point;
4701 while ((split_point = yyextra->current->name.find("::")) != DString::npos)
4702 {
4703 std::shared_ptr<Entry> new_current = std::make_shared<Entry>(*yyextra->current);
4704 yyextra->current->program.str(std::string());
4705 new_current->name = yyextra->current->name.mid(split_point + 2);
4706 yyextra->current->name = yyextra->current->name.left(split_point);
4707 if (yyextra->current->name.startsWith("inline ")) // C++20 style nested inline namespace syntax
4708 {
4709 yyextra->current->name = yyextra->current->name.mid(7);
4710 yyextra->current->spec.setInline(true);
4711 }
4712 if (!yyextra->current_root->name.empty()) yyextra->current->name.prepend(yyextra->current_root->name+"::");
4713
4714 yyextra->current_root->moveToSubEntryAndKeep(yyextra->current);
4715 yyextra->current_root = yyextra->current;
4716 yyextra->current = new_current;
4717 }
4718 // restore documentation values
4719 yyextra->current->doc = doc;
4720 yyextra->current->docLine = docLine;
4721 yyextra->current->docFile = docFile;
4722 yyextra->current->brief = brief;
4723 yyextra->current->briefLine = briefLine;
4724 yyextra->current->briefFile = briefFile;
4725 yyextra->current->groups = groups;
4726 yyextra->current->anchors = anchors;
4727 yyextra->current->sli = sli;
4728 yyextra->current->rqli = rqli;
4729 }
4730 DString &cn = yyextra->current->name;
4731 if (cn.startsWith("inline ")) // C++20 style nested inline namespace syntax
4732 {
4733 cn = cn.mid(7);
4734 yyextra->current->spec.setInline(true);
4735 }
4736 DString rn = yyextra->current_root->name;
4737 //printf("cn='%s' rn='%s' yyextra->isTypedef=%d\n",qPrint(cn),qPrint(rn),yyextra->isTypedef);
4738 if (!cn.empty() && !rn.empty())
4739 {
4740 prependScope(yyscanner);
4741 }
4742 if (yyextra->isTypedef && cn.empty())
4743 {
4744 //printf("Typedef Name\n");
4745 BEGIN( TypedefName );
4746 }
4747 else
4748 {
4749 if (yyextra->current->section.isEnum() || yyextra->current->spec.isEnum())
4750 {
4751 yyextra->current->program << ','; // add field terminator
4752 }
4753 // add compound definition to the tree
4754 yyextra->current->args=removeRedundantWhiteSpace(yyextra->current->args);
4755 // was: yyextra->current->args.simplifyWhiteSpace();
4756 yyextra->current->type = yyextra->current->type.simplifyWhiteSpace();
4757 yyextra->current->name = yyextra->current->name.stripWhiteSpace();
4758 //printf("adding '%s' '%s' '%s' brief=%s yyextra->insideObjC=%d %x\n",qPrint(yyextra->current->type),qPrint(yyextra->current->name),qPrint(yyextra->current->args),qPrint(yyextra->current->brief),yyextra->insideObjC,yyextra->current->section);
4759 if (yyextra->insideObjC &&
4760 (yyextra->current->spec.isInterface() || yyextra->current->spec.isCategory())
4761 ) // method definition follows
4762 {
4763 BEGIN( ReadBodyIntf ) ;
4764 }
4765 else
4766 {
4767 yyextra->memspecEntry = yyextra->current;
4768 if (yyextra->isTypedef)
4769 {
4770 yyextra->current_root->moveToSubEntryAndKeep( yyextra->current ) ;
4771 yyextra->current = std::make_shared<Entry>(*yyextra->current);
4772 }
4773 else
4774 {
4775 yyextra->current_root->moveToSubEntryAndRefresh( yyextra->current ) ;
4776 yyextra->current = std::make_shared<Entry>(*yyextra->memspecEntry);
4777 }
4778 if (yyextra->current->section.isNamespace() ||
4779 yyextra->current->spec.isInterface() ||
4780 yyextra->insideJava || yyextra->insidePHP || yyextra->insideCS || yyextra->insideD || yyextra->insideJS ||
4781 yyextra->insideSlice
4782 )
4783 { // namespaces and interfaces and java classes ends with a closing bracket without semicolon
4784 yyextra->current->reset();
4785 yyextra->current_root = std::move(original_root); // restore scope from before namespace descent
4786 initEntry(yyscanner);
4787 yyextra->memspecEntry.reset();
4788 BEGIN( FindMembers ) ;
4789 }
4790 else
4791 {
4792 if (!yyextra->isTypedef) // for a typedef we do not reset the documentation
4793 {
4794 yyextra->current->doc.clear();
4795 yyextra->current->brief.clear();
4796 }
4797 BEGIN( MemberSpec ) ;
4798 }
4799 }
4800 }
4801 }
4802 }
void clear()
Definition dstring.h:218
bool startsWith(const char *s) const
Definition dstring.h:604
4803<ReadBody>"}"{BN}+"typedef"{BN}+ {
4804 lineCount(yyscanner);
4805 if ( yyextra->curlyCount>0 )
4806 {
4807 yyextra->current->program << yytext ;
4808 --yyextra->curlyCount ;
4809 }
4810 else
4811 {
4812 yyextra->isTypedef = true;
4813 yyextra->current->endBodyLine = yyextra->yyLineNr;
4814 DString &cn = yyextra->current->name;
4815 DString rn = yyextra->current_root->name;
4816 if (!cn.empty() && !rn.empty())
4817 {
4818 prependScope(yyscanner);
4819 }
4820 BEGIN( TypedefName );
4821 }
4822 }
4823<TypedefName>("const"|"volatile"){BN} { // late "const" or "volatile" keyword
4824 lineCount(yyscanner);
4825 yyextra->current->type.prepend(yytext);
4826 }
4827<TypedefName>{ID} {
4828 if (yyextra->current->section.isEnum() || yyextra->current->spec.isEnum())
4829 {
4830 yyextra->current->program << ","; // add field terminator
4831 }
4832 yyextra->current->name=yytext;
4833 prependScope(yyscanner);
4834 yyextra->current->args = yyextra->current->args.simplifyWhiteSpace();
4835 yyextra->current->type = yyextra->current->type.simplifyWhiteSpace();
4836 //printf("Adding compound %s %s %s\n",qPrint(yyextra->current->type),qPrint(yyextra->current->name),qPrint(yyextra->current->args));
4837 if (!yyextra->firstTypedefEntry)
4838 {
4839 yyextra->firstTypedefEntry = yyextra->current;
4840 }
4841 yyextra->current_root->moveToSubEntryAndRefresh( yyextra->current ) ;
4842 initEntry(yyscanner);
4843 yyextra->isTypedef=true; // to undo reset by initEntry(yyscanner)
4844 BEGIN(MemberSpecSkip);
4845 }
4846<TypedefName>";" { /* typedef of anonymous type */
4847 yyextra->current->name = generateAnonymousAnchor(yyextra->fileName,yyextra->anonCount++);
4848 if (yyextra->current->section.isEnum() || yyextra->current->spec.isEnum())
4849 {
4850 yyextra->current->program << ','; // add field terminator
4851 }
4852 // add compound definition to the tree
4853 yyextra->current->args = yyextra->current->args.simplifyWhiteSpace();
4854 yyextra->current->type = yyextra->current->type.simplifyWhiteSpace();
4855 yyextra->memspecEntry = yyextra->current;
4856 yyextra->current_root->moveToSubEntryAndRefresh( yyextra->current ) ;
4857 initEntry(yyscanner);
4858 unput(';');
4859 BEGIN( MemberSpec ) ;
4860 }
4861<MemberSpec>([*&]*{BN}*)*{ID}{BN}*("["[^\‍]\n]*"]")* { // the [] part could be improved.
4862 lineCount(yyscanner);
4863 int i=0,l=(int)yyleng;
4864 while (i<l && (!isId(yytext[i]))) i++;
4865 yyextra->msName = DString(yytext).right(l-i).stripWhiteSpace();
4866 if (size_t j=yyextra->msName.find("[") ; j!=DString::npos)
4867 {
4868 yyextra->msArgs=yyextra->msName.mid(j);
4869 yyextra->msName=yyextra->msName.left(j);
4870 }
4871 yyextra->msType=DString(yytext).left(i);
4872
4873 // handle *pName in: typedef { ... } name, *pName;
4874 if (yyextra->firstTypedefEntry)
4875 {
4876 if (yyextra->firstTypedefEntry->spec.isStruct())
4877 {
4878 yyextra->msType.prepend("struct "+yyextra->firstTypedefEntry->name);
4879 }
4880 else if (yyextra->firstTypedefEntry->spec.isUnion())
4881 {
4882 yyextra->msType.prepend("union "+yyextra->firstTypedefEntry->name);
4883 }
4884 else if (yyextra->firstTypedefEntry->section.isEnum())
4885 {
4886 yyextra->msType.prepend("enum "+yyextra->firstTypedefEntry->name);
4887 }
4888 else
4889 {
4890 yyextra->msType.prepend(yyextra->firstTypedefEntry->name);
4891 }
4892 }
4893 }
DString right(size_t len) const
Definition dstring.h:315
bool isId(int c)
Returns true if c is a valid character for an identifier.
Definition dstring.h:899
4894<MemberSpec>"(" { // function with struct return type
4895 addType(yyscanner);
4896 yyextra->current->name = yyextra->msName;
4897 yyextra->current->spec = TypeSpecifier();
4898 unput('(');
4899 BEGIN(FindMembers);
4900 }
4901<MemberSpec>[,;] {
4902 //printf("msName=%s\n",qPrint(yyextra->msName));
4903 if (yyextra->msName.empty() && !yyextra->current->name.empty())
4904 {
4905 // see if the compound does not have a name or is yyextra->inside another
4906 // anonymous compound. If so we insert a
4907 // special 'anonymous' variable.
4908 //Entry *p=yyextra->current_root;
4909 const Entry *p=yyextra->current.get();
4910 while (p)
4911 {
4912 // only look for class scopes, not namespace scopes
4913 if (p->section.isCompound() && !p->name.empty())
4914 {
4915 //printf("Trying scope '%s'\n",qPrint(p->name));
4916 size_t i=p->name.rfind("::");
4917 size_t pi = i==DString::npos ? 0 : i+2;
4918 if (p->name.at(pi)=='@')
4919 {
4920 // anonymous compound yyextra->inside -> insert dummy variable name
4921 //printf("Adding anonymous variable for scope %s\n",qPrint(p->name));
4922 yyextra->msName = generateAnonymousAnchor(yyextra->fileName,yyextra->anonCount++);
4923 break;
4924 }
4925 }
4926 //p=p->parent;
4927 if (p==yyextra->current.get()) p=yyextra->current_root.get(); else p=p->parent();
4928 }
4929 }
4930 //printf("yyextra->msName=%s yyextra->current->name=%s\n",qPrint(yyextra->msName),qPrint(yyextra->current->name));
4931 if (!yyextra->msName.empty()
4932 /*&& yyextra->msName!=yyextra->current->name*/) // skip typedef T {} T;, removed due to bug608493
4933 {
4934 bool typedefHidesStruct = Config_getBool(TYPEDEF_HIDES_STRUCT);
4935 // case 1: typedef struct _S { ... } S_t;
4936 // -> omit typedef and use S_t as the struct name
4937 if (typedefHidesStruct &&
4938 yyextra->isTypedef &&
4939 ((yyextra->current->spec.isStruct() || yyextra->current->spec.isUnion()) || yyextra->current->section.isEnum()) &&
4940 yyextra->msType.stripWhiteSpace().empty() &&
4941 yyextra->memspecEntry)
4942 {
4943 yyextra->memspecEntry->name=yyextra->msName;
4944 }
4945 else // case 2: create a typedef field
4946 {
4947 std::shared_ptr<Entry> varEntry=std::make_shared<Entry>();
4948 varEntry->lang = yyextra->language;
4949 varEntry->protection = yyextra->current->protection ;
4950 varEntry->mtype = yyextra->current->mtype;
4951 varEntry->virt = yyextra->current->virt;
4952 varEntry->isStatic = yyextra->current->isStatic;
4953 varEntry->section = EntryType::makeVariable();
4954 varEntry->name = yyextra->msName.stripWhiteSpace();
4955 varEntry->type = yyextra->current->type.simplifyWhiteSpace()+" ";
4956 varEntry->args = yyextra->msArgs;
4957 if (yyextra->isTypedef)
4958 {
4959 varEntry->type.prepend("typedef ");
4960 // //printf("yyextra->current->name = %s %s\n",qPrint(yyextra->current->name),qPrint(yyextra->msName));
4961 }
4962 if (typedefHidesStruct &&
4963 yyextra->isTypedef &&
4964 (yyextra->current->spec.isStruct() || yyextra->current->spec.isUnion()) &&
4965 yyextra->memspecEntry
4966 ) // case 1: use S_t as type for pS_t in "typedef struct _S {} S_t, *pS_t;"
4967 {
4968 varEntry->type+=yyextra->memspecEntry->name+yyextra->msType;
4969 }
4970 else // case 2: use _S as type for for pS_t
4971 {
4972 varEntry->type+=yyextra->current->name+yyextra->msType;
4973 }
4974 varEntry->fileName = yyextra->fileName;
4975 varEntry->startLine = yyextra->yyLineNr;
4976 varEntry->startColumn = yyextra->yyColNr;
4977 varEntry->doc = yyextra->current->doc;
4978 varEntry->brief = yyextra->current->brief;
4979 varEntry->mGrpId = yyextra->current->mGrpId;
4980 varEntry->initializer.str(yyextra->current->initializer.str());
4981 varEntry->groups = yyextra->current->groups;
4982 varEntry->sli = yyextra->current->sli;
4983
4984 //printf("Add: type='%s',name='%s',args='%s' brief=%s doc=%s\n",
4985 // qPrint(varEntry->type),qPrint(varEntry->name),
4986 // qPrint(varEntry->args),qPrint(varEntry->brief),qPrint(varEntry->doc));
4987 yyextra->current_root->moveToSubEntryAndKeep(varEntry);
4988 }
4989 }
4990 if (*yytext==';') // end of a struct/class ...
4991 {
4992 if (!yyextra->isTypedef && yyextra->msName.empty() &&
4993 yyextra->memspecEntry && yyextra->current->section.isCompound())
4994 { // case where a class/struct has a doc block after it
4995 if (!yyextra->current->doc.empty())
4996 {
4997 yyextra->memspecEntry->doc += yyextra->current->doc;
4998 }
4999 if (!yyextra->current->brief.empty())
5000 {
5001 yyextra->memspecEntry->brief += yyextra->current->brief;
5002 }
5003 }
5004 yyextra->msType.clear();
5005 yyextra->msName.clear();
5006 yyextra->msArgs.clear();
5007 yyextra->isTypedef=false;
5008 yyextra->firstTypedefEntry.reset();
5009 yyextra->memspecEntry.reset();
5010 yyextra->current->reset();
5011 initEntry(yyscanner);
5012 BEGIN( FindMembers );
5013 }
5014 else
5015 {
5016 yyextra->current->doc.clear();
5017 yyextra->current->brief.clear();
5018 }
5019
5020 }
size_t rfind(char c, size_t pos=npos) const
Definition dstring.h:248
char & at(size_t i)
Returns a reference to the character at index i.
Definition dstring.h:690
Represents an unstructured piece of information, about an entity found in the sources.
Definition entry.h:115
Entry * parent() const
Definition entry.h:133
EntryType section
entry type (see Sections);
Definition entry.h:171
DString name
member name
Definition entry.h:173
ENTRY_TYPES constexpr bool isCompound() const noexcept
Definition types.h:863
5021<MemberSpec>"=" {
5022 yyextra->lastInitializerContext=YY_START;
5023 yyextra->sharpCount=0;
5024 yyextra->initBracketCount=0;
5025 yyextra->current->initializer.str(yytext);
5026 BEGIN(ReadInitializer);
5027 /* BEGIN(MemberSpecSkip); */
5028 }
5029 /*
5030<MemberSpecSkip>"{" {
5031 yyextra->curlyCount=0;
5032 yyextra->lastCurlyContext = MemberSpecSkip;
5033 yyextra->previous = yyextra->current;
5034 BEGIN(SkipCurly);
5035 }
5036 */
5037<MemberSpecSkip>"," { BEGIN(MemberSpec); }
5038<MemberSpecSkip>";" { unput(';'); BEGIN(MemberSpec); }
5039<ReadBody,ReadNSBody,ReadBodyIntf>{BN}{1,80} { yyextra->current->program << yytext ;
5040 lineCount(yyscanner) ;
5041 }
5042<ReadBodyIntf>"@end"/[^a-z_A-Z0-9] { // end of Objective C block
5043 yyextra->current_root->moveToSubEntryAndRefresh( yyextra->current ) ;
5044 initEntry(yyscanner);
5045 yyextra->language = yyextra->current->lang = SrcLangExt::Cpp; // see bug746361
5046 yyextra->insideObjC=false;
5047 BEGIN( FindMembers );
5048 }
5049<ReadBody,ReadNSBody,ReadBodyIntf>\\. { yyextra->current->program << yytext ; }
5050<ReadBody,ReadNSBody,ReadBodyIntf>. { yyextra->current->program << yytext ; }
5051
5052<FindMembers>"("/{BN}*"::"*{BN}*({TSCOPE}{BN}*"::")*{TSCOPE}{BN}*")"{BN}*"(" | /* typedef void (A<int>::func_t)(args...) */
5053<FindMembers>("("({BN}*"::"*{BN}*{TSCOPE}{BN}*"::")*({BN}*[*&\^]{BN}*)+)+ { /* typedef void (A::*ptr_t)(args...) or int (*func(int))[], the ^ is for Obj-C blocks */
5054 if (yyextra->insidePHP) // reference parameter
5055 {
5056 REJECT
5057 }
5058 else
5059 {
5060 yyextra->current->bodyLine = yyextra->yyLineNr;
5061 yyextra->current->bodyColumn = yyextra->yyColNr;
5062 lineCount(yyscanner);
5063 addType(yyscanner);
5064 yyextra->funcPtrType=yytext;
5065 yyextra->roundCount=0;
5066 //yyextra->current->type += yytext;
5067 BEGIN( FuncPtr );
5068 }
5069 }
5070<FuncPtr>{SCOPENAME} {
5071 yyextra->current->name = yytext;
5072 if (nameIsOperator(yyextra->current->name))
5073 {
5074 BEGIN( FuncPtrOperator );
5075 }
5076 else
5077 {
5078 if (yyextra->current->name=="const" || yyextra->current->name=="volatile")
5079 {
5080 yyextra->funcPtrType += yyextra->current->name;
5081 }
5082 else
5083 {
5084 BEGIN( EndFuncPtr );
5085 }
5086 }
5087 }
5088<FuncPtr>. {
5089 //printf("error: FuncPtr '%c' unexpected at line %d of %s\n",*yytext,yyextra->yyLineNr,yyextra->fileName);
5090 }
5091<FuncPtrOperator>"("{BN}*")"{BNopt}/"(" {
5092 yyextra->current->name += yytext;
5093 yyextra->current->name = yyextra->current->name.simplifyWhiteSpace();
5094 lineCount(yyscanner);
5095 }
5096<FuncPtrOperator>\n {
5097 lineCount(yyscanner);
5098 yyextra->current->name += *yytext;
5099 }
5100<FuncPtrOperator>"(" {
5101 unput(*yytext);
5102 BEGIN( EndFuncPtr );
5103 }
5104<FuncPtrOperator>. {
5105 yyextra->current->name += *yytext;
5106 }
5107<EndFuncPtr>")"{BNopt}/";" { // a variable with extra braces
5108 lineCount(yyscanner);
5109 yyextra->current->type+=yyextra->funcPtrType.mid(1);
5110 BEGIN(FindMembers);
5111 }
5112<EndFuncPtr>")"{BNopt}/"(" { // a function pointer
5113 lineCount(yyscanner);
5114 if (yyextra->funcPtrType!="(") // not just redundant braces
5115 {
5116 yyextra->current->type+=yyextra->funcPtrType+")";
5117 }
5118 BEGIN(FindMembers);
5119 }
5120<EndFuncPtr>")"{BNopt}/"[" { // an array of variables
5121 lineCount(yyscanner);
5122 yyextra->current->type+=yyextra->funcPtrType;
5123 yyextra->current->args += ")";
5124 BEGIN(FindMembers);
5125 }
5126<EndFuncPtr>"(" { // a function returning a function or
5127 // a function returning a pointer to an array
5128 yyextra->current->args += *yytext ;
5129 //yyextra->roundCount=0;
5130 //BEGIN( FuncFunc );
5131 yyextra->current->bodyLine = yyextra->yyLineNr;
5132 yyextra->current->bodyColumn = yyextra->yyColNr;
5133 yyextra->currentArgumentContext = FuncFuncEnd;
5134 yyextra->fullArgString=yyextra->current->args;
5135 yyextra->copyArgString=&yyextra->current->args;
5136 BEGIN( ReadFuncArgType ) ;
5137 }
5138<EndFuncPtr>"["[^\n\‍]]*"]" {
5139 yyextra->funcPtrType+=yytext;
5140 }
5141<EndFuncPtr>")" {
5142 BEGIN(FindMembers);
5143 }
5144<FuncFunc>"(" {
5145 yyextra->current->args += *yytext ;
5146 ++yyextra->roundCount;
5147 }
5148<FuncFunc>")" {
5149 yyextra->current->args += *yytext ;
5150 if ( yyextra->roundCount )
5151 --yyextra->roundCount;
5152 else
5153 {
5154 BEGIN(FuncFuncEnd);
5155 }
5156 }
5157<FuncFuncEnd>")"{BN}*"(" {
5158 lineCount(yyscanner);
5159 yyextra->current->type+=yyextra->funcPtrType+")(";
5160 BEGIN(FuncFuncType);
5161 }
5162<FuncFuncEnd>")"{BNopt}/[;{] {
5163 lineCount(yyscanner);
5164 yyextra->current->type+=yyextra->funcPtrType.mid(1);
5165 BEGIN(SFunction);
5166 }
5167<FuncFuncEnd>")"{BNopt}/"[" { // function returning a pointer to an array
5168 lineCount(yyscanner);
5169 yyextra->current->type+=yyextra->funcPtrType;
5170 yyextra->current->args+=")";
5171 BEGIN(FuncFuncArray);
5172 }
5173<FuncFuncEnd>. {
5174 yyextra->current->args += *yytext;
5175 }
5176<FuncFuncType>"(" {
5177 yyextra->current->type += *yytext;
5178 yyextra->roundCount++;
5179 }
5180<FuncFuncType>")" {
5181 yyextra->current->type += *yytext;
5182 if (yyextra->roundCount)
5183 --yyextra->roundCount;
5184 else
5185 BEGIN(SFunction);
5186 }
5187<FuncFuncType>{BN}*","{BN}* { lineCount(yyscanner) ; yyextra->current->type += ", " ; }
5188<FuncFuncType>{BN}+ { lineCount(yyscanner) ; yyextra->current->type += ' ' ; }
5189<FuncFuncType>. {
5190 yyextra->current->type += *yytext;
5191 }
5192<FindMembers>"("/{BN}*{ID}{BN}*"*"{BN}*{ID}*")"{BN}*"(" { // for catching typedef void (__stdcall *f)() like definitions
5193 if (yyextra->current->type.startsWith("typedef") &&
5194 yyextra->current->bodyLine==-1)
5195 // the bodyLine check is to prevent this guard to be true more than once
5196 {
5197 yyextra->current->bodyLine = yyextra->yyLineNr;
5198 yyextra->current->bodyColumn = yyextra->yyColNr;
5199 BEGIN( GetCallType );
5200 }
5201 else if (!yyextra->current->name.empty()) // normal function
5202 {
5203 yyextra->current->args = yytext;
5204 yyextra->current->bodyLine = yyextra->yyLineNr;
5205 yyextra->current->bodyColumn = yyextra->yyColNr;
5206 yyextra->currentArgumentContext = FuncQual;
5207 yyextra->fullArgString=yyextra->current->args;
5208 yyextra->copyArgString=&yyextra->current->args;
5209 BEGIN( ReadFuncArgType ) ;
5210 //printf(">>> Read function arguments!\n");
5211 }
5212 }
5213<GetCallType>{BN}*{ID}{BN}*"*" {
5214 lineCount(yyscanner);
5215 addType(yyscanner);
5216 yyextra->funcPtrType="(";
5217 yyextra->funcPtrType+=yytext;
5218 yyextra->roundCount=0;
5219 BEGIN( FuncPtr );
5220 }
5221<FindMembers>"(" {
5222 if (!yyextra->current->name.empty())
5223 {
5224 yyextra->current->args = yytext;
5225 yyextra->current->bodyLine = yyextra->yyLineNr;
5226 yyextra->current->bodyColumn = yyextra->yyColNr;
5227 yyextra->currentArgumentContext = FuncQual;
5228 yyextra->fullArgString=yyextra->current->args;
5229 yyextra->copyArgString=&yyextra->current->args;
5230 BEGIN( ReadFuncArgType ) ;
5231 //printf(">>> Read function arguments yyextra->current->argList.size()=%d\n",yyextra->current->argList.size());
5232 }
5233 }
5234
5235 /*- Function argument reading rules ---------------------------------------*/
5236
5237<ReadFuncArgType>[^ \/\r\t\n\‍[\‍]\‍)\‍(\"\'#]+ { *yyextra->copyArgString+=yytext;
5238 if (yyextra->insideCS) yyextra->fullArgString+=substitute(yytext,".","::");
5239 else yyextra->fullArgString+=yytext;
5240 }
5241<CopyArgString,CopyArgPHPString>[^\n\\\"\']+ { *yyextra->copyArgString+=yytext;
5242 yyextra->fullArgString+=yytext;
5243 }
5244<CopyArgRound>[^\/\n\‍)\‍(\"\']+ {
5245 *yyextra->copyArgString+=yytext;
5246 yyextra->fullArgString+=yytext;
5247 }
5248<CopyArgSquare>[^\/\n\‍]\‍[\"\']+ {
5249 *yyextra->copyArgString+=yytext;
5250 yyextra->fullArgString+=yytext;
5251 }
5252<ReadFuncArgType,ReadTempArgs>{BN}* {
5253 *yyextra->copyArgString+=" ";
5254 yyextra->fullArgString+=" ";
5255 lineCount(yyscanner);
5256 }
5257<ReadFuncArgType,CopyArgRound,CopyArgSquare,CopyArgSharp,ReadTempArgs>{RAWBEGIN} {
5258 yyextra->delimiter = extractBeginRawStringDelimiter(yytext);
5259 yyextra->lastRawStringContext = YY_START;
5260 yyextra->pCopyRawString = yyextra->copyArgString;
5261 *yyextra->pCopyRawString+=yytext;
5262 yyextra->fullArgString+=yytext;
5263 BEGIN(RawString);
5264 }
5265<ReadFuncArgType,CopyArgRound,CopyArgSquare,CopyArgSharp,ReadTempArgs>\" {
5266 *yyextra->copyArgString+=*yytext;
5267 yyextra->fullArgString+=*yytext;
5268 yyextra->lastCopyArgStringContext = YY_START;
5269 BEGIN( CopyArgString );
5270 }
5271<ReadFuncArgType>"[" {
5272 if (!yyextra->insidePHP) REJECT;
5273 *yyextra->copyArgString+=*yytext;
5274 yyextra->fullArgString+=*yytext;
5275 yyextra->argSquareCount=0;
5276 yyextra->lastCopyArgContext = YY_START;
5277 BEGIN( CopyArgSquare );
5278 }
5279<ReadFuncArgType,ReadTempArgs>"(" {
5280 *yyextra->copyArgString+=*yytext;
5281 yyextra->fullArgString+=*yytext;
5282 yyextra->argRoundCount=0;
5283 yyextra->lastCopyArgContext = YY_START;
5284 BEGIN( CopyArgRound );
5285 }
5286<ReadFuncArgType>")" {
5287 *yyextra->copyArgString+=*yytext;
5288 yyextra->fullArgString+=*yytext;
5289 yyextra->current->argList = *stringToArgumentList(yyextra->language, yyextra->fullArgString);
5290 if (yyextra->insideJS)
5291 {
5292 fixArgumentListForJavaScript(yyextra->current->argList);
5293 }
5294 handleParametersCommentBlocks(yyscanner,yyextra->current->argList);
5295
5296 /* remember the yyextra->current documentation block, since
5297 we could overwrite it with the documentation of
5298 a function argument, which we then have to correct later
5299 on
5300 */
5301 yyextra->docBackup = yyextra->current->doc;
5302 yyextra->briefBackup = yyextra->current->brief;
5303
5304 BEGIN( yyextra->currentArgumentContext );
5305 }
std::unique_ptr< ArgumentList > stringToArgumentList(SrcLangExt lang, const DString &argsString, DString *extraTypeChars=nullptr)
Definition defargs.l:821
5306 /* a special comment */
5307<ReadFuncArgType,ReadTempArgs>({CCS}[*!]|{CPPC}[/!])("<"?) {
5308 if (yyextra->currentArgumentContext==DefineEnd)
5309 {
5310 // for defines we interpret a comment
5311 // as documentation for the define
5312 int i;for (i=(int)yyleng-1;i>=0;i--)
5313 {
5314 unput(yytext[i]);
5315 }
5316 yyextra->current->argList = *stringToArgumentList(yyextra->language, yyextra->fullArgString);
5317 handleParametersCommentBlocks(yyscanner,yyextra->current->argList);
5318 BEGIN( yyextra->currentArgumentContext );
5319 }
5320 else // not a define
5321 {
5322 // for functions we interpret a comment
5323 // as documentation for the argument
5324 yyextra->fullArgString+=yytext;
5325 yyextra->lastCopyArgChar=0;
5326 yyextra->lastCommentInArgContext=YY_START;
5327 if (yytext[1]=='/')
5328 BEGIN( CopyArgCommentLine );
5329 else
5330 BEGIN( CopyArgComment );
5331 }
5332 }
5333 /* a non-special comment */
5334<ReadFuncArgType,ReadTempArgs>{CCS}{CCE} { /* empty comment */ }
5335<ReadFuncArgType,ReadTempArgs>{CCS} {
5336 yyextra->lastCContext = YY_START;
5337 BEGIN( SkipComment );
5338 }
5339<ReadFuncArgType,ReadTempArgs>{CPPC} {
5340 yyextra->lastCContext = YY_START;
5341 BEGIN( SkipCxxComment );
5342 }
5343 /*
5344<ReadFuncArgType,ReadTempArgs>"'#" { if (yyextra->insidePHP)
5345 REJECT;
5346 *yyextra->copyArgString+=yytext;
5347 yyextra->fullArgString+=yytext;
5348 }
5349<ReadFuncArgType,ReadTempArgs>"#" {
5350 if (!yyextra->insidePHP)
5351 REJECT;
5352 yyextra->lastCContext = YY_START;
5353 BEGIN( SkipCxxComment );
5354 }
5355 */
5356 /* ')' followed by a special comment */
5357<ReadFuncArgType>")"{BN}*({CCS}[*!]|{CPPC}[/!])"<" {
5358 lineCount(yyscanner);
5359 if (yyextra->currentArgumentContext==DefineEnd)
5360 {
5361 // for defines we interpret a comment
5362 // as documentation for the define
5363 int i;for (i=(int)yyleng-1;i>0;i--)
5364 {
5365 unput(yytext[i]);
5366 }
5367 *yyextra->copyArgString+=*yytext;
5368 yyextra->fullArgString+=*yytext;
5369 yyextra->current->argList = *stringToArgumentList(yyextra->language, yyextra->fullArgString);
5370 handleParametersCommentBlocks(yyscanner,yyextra->current->argList);
5371 BEGIN( yyextra->currentArgumentContext );
5372 }
5373 else
5374 {
5375 // for functions we interpret a comment
5376 // as documentation for the yyextra->last argument
5377 yyextra->lastCopyArgChar=*yytext;
5378 DString text=&yytext[1];
5379 text=text.stripWhiteSpace();
5380 yyextra->lastCommentInArgContext=YY_START;
5381 yyextra->fullArgString+=text;
5382 if (text.find("//")!=DString::npos)
5383 BEGIN( CopyArgCommentLine );
5384 else
5385 BEGIN( CopyArgComment );
5386 }
5387 }
5388<CopyArgComment>^{B}*"*"+/{BN}+
5389<CopyArgComment>[^\n\\\@\*]+ { yyextra->fullArgString+=yytext; }
5390<CopyArgComment>{CCE} { yyextra->fullArgString+=yytext;
5391 if (yyextra->lastCopyArgChar!=0)
5392 unput(yyextra->lastCopyArgChar);
5393 BEGIN( yyextra->lastCommentInArgContext );
5394 }
5395<CopyArgCommentLine>\n { yyextra->fullArgString+=yytext;
5396 lineCount(yyscanner);
5397 if (yyextra->lastCopyArgChar!=0)
5398 unput(yyextra->lastCopyArgChar);
5399 BEGIN( yyextra->lastCommentInArgContext );
5400 }
5401<CopyArgCommentLine>{CMD}"startuml"/[^a-z_A-Z0-9\-] { // verbatim type command (which could contain nested comments!)
5402 yyextra->docBlockName="uml";
5403 yyextra->fullArgString+=yytext;
5404 BEGIN(CopyArgVerbatim);
5405 }
5406<CopyArgCommentLine>{CMD}("verbatim"|"iliteral"|"latexonly"|"htmlonly"|"xmlonly"|"manonly"|"rtfonly"|"docbookonly"|"dot"|"msc"|"mermaid"|"code")/[^a-z_A-Z0-9\-] { // verbatim command (which could contain nested comments!)
5407 yyextra->docBlockName=&yytext[1];
5408 yyextra->fullArgString+=yytext;
5409 BEGIN(CopyArgVerbatim);
5410 }
5411<CopyArgCommentLine>{CMD}("f$"|"f["|"f{"|"f(") {
5412 yyextra->docBlockName=&yytext[1];
5413 if (yyextra->docBlockName.at(1)=='[')
5414 {
5415 yyextra->docBlockName.at(1)=']';
5416 }
5417 if (yyextra->docBlockName.at(1)=='{')
5418 {
5419 yyextra->docBlockName.at(1)='}';
5420 }
5421 if (yyextra->docBlockName.at(1)=='(')
5422 {
5423 yyextra->docBlockName.at(1)=')';
5424 }
5425 yyextra->fullArgString+=yytext;
5426 BEGIN(CopyArgVerbatim);
5427 }
5428<CopyArgVerbatim>{CMD}("endverbatim"|"endiliteral"|"endlatexonly"|"endhtmlonly"|"endxmlonly"|"enddocbookonly"|"endmanonly"|"endrtfonly"|"enddot"|"endmsc"|"endmermaid"|"enduml"|"endcode")/[^a-z_A-Z0-9\-] { // end of verbatim block
5429 yyextra->fullArgString+=yytext;
5430 if (&yytext[4]==yyextra->docBlockName)
5431 {
5432 yyextra->docBlockName="";
5433 BEGIN(CopyArgCommentLine);
5434 }
5435 }
5436<CopyArgVerbatim>{CMD}("f$"|"f]"|"f}"|"f)") { // end of verbatim block
5437 yyextra->fullArgString+=yytext;
5438 if (yyextra->docBlockName==&yytext[1])
5439 {
5440 yyextra->docBlockName="";
5441 BEGIN(CopyArgCommentLine);
5442 }
5443 }
5444<CopyArgCommentLine>[^\\\@\n]+ { yyextra->fullArgString+=yytext; }
5445<CopyArgCommentLine>. { yyextra->fullArgString+=*yytext; }
5446<CopyArgComment,CopyArgVerbatim>\n { yyextra->fullArgString+=*yytext; lineCount(yyscanner); }
5447<CopyArgComment,CopyArgVerbatim>. { yyextra->fullArgString+=*yytext; }
5448<CopyArgComment>{CMD}("brief"|"short"){B}+ {
5449 warn(yyextra->fileName,yyextra->yyLineNr,
5450 "Ignoring {:c}brief command inside argument documentation",*yytext
5451 );
5452 yyextra->fullArgString+=' ';
5453 }
5454<ReadTempArgs>"<" {
5455 *yyextra->copyArgString+=*yytext;
5456 yyextra->fullArgString+=*yytext;
5457 yyextra->argSharpCount=1;
5458 BEGIN( CopyArgSharp );
5459 }
5460<ReadTempArgs>">" {
5461 *yyextra->copyArgString+=*yytext;
5462 yyextra->fullArgString+=*yytext;
5463 //printf("end template list '%s'\n",qPrint(*yyextra->copyArgString));
5464 *yyextra->currentArgumentList = *stringToArgumentList(yyextra->language, yyextra->fullArgString);
5465 handleParametersCommentBlocks(yyscanner,yyextra->current->tArgLists.back());
5466 BEGIN( yyextra->currentArgumentContext );
5467 }
5468<CopyArgRound>"(" {
5469 yyextra->argRoundCount++;
5470 *yyextra->copyArgString+=*yytext;
5471 yyextra->fullArgString+=*yytext;
5472 }
5473<CopyArgRound>")" {
5474 *yyextra->copyArgString+=*yytext;
5475 yyextra->fullArgString+=*yytext;
5476 if (yyextra->argRoundCount>0)
5477 yyextra->argRoundCount--;
5478 else
5479 BEGIN( yyextra->lastCopyArgContext );
5480 }
5481<CopyArgSquare>"[" {
5482 yyextra->argSquareCount++;
5483 *yyextra->copyArgString+=*yytext;
5484 yyextra->fullArgString+=*yytext;
5485 }
5486<CopyArgSquare>"]" {
5487 *yyextra->copyArgString+=*yytext;
5488 yyextra->fullArgString+=*yytext;
5489 if (yyextra->argSquareCount>0)
5490 yyextra->argSquareCount--;
5491 else
5492 BEGIN( yyextra->lastCopyArgContext );
5493 }
5494<CopyArgSharp>"(" {
5495 *yyextra->copyArgString+=*yytext;
5496 yyextra->fullArgString+=*yytext;
5497 yyextra->argRoundCount=0;
5498 yyextra->lastCopyArgContext = YY_START;
5499 BEGIN( CopyArgRound );
5500 }
5501<CopyArgSharp>"<" {
5502 yyextra->argSharpCount++;
5503 //printf("yyextra->argSharpCount++=%d copy\n",yyextra->argSharpCount);
5504 *yyextra->copyArgString+=*yytext;
5505 yyextra->fullArgString+=*yytext;
5506 }
5507<CopyArgSharp>">" {
5508 *yyextra->copyArgString+=*yytext;
5509 yyextra->fullArgString+=*yytext;
5510 yyextra->argSharpCount--;
5511 if (yyextra->argSharpCount>0)
5512 {
5513 //printf("yyextra->argSharpCount--=%d copy\n",yyextra->argSharpCount);
5514 }
5515 else
5516 {
5517 BEGIN( ReadTempArgs );
5518 //printf("end of yyextra->argSharpCount\n");
5519 }
5520 }
5521<CopyArgString,CopyArgPHPString>\\. {
5522 *yyextra->copyArgString+=yytext;
5523 yyextra->fullArgString+=yytext;
5524 }
5525<CopyArgString>\" {
5526 *yyextra->copyArgString+=*yytext;
5527 yyextra->fullArgString+=*yytext;
5528 BEGIN( yyextra->lastCopyArgStringContext );
5529 }
5530<CopyArgPHPString>\' {
5531 *yyextra->copyArgString+=*yytext;
5532 yyextra->fullArgString+=*yytext;
5533 BEGIN( yyextra->lastCopyArgStringContext );
5534 }
5535<ReadFuncArgType,ReadTempArgs,CopyArgRound,CopyArgSquare,CopyArgSharp>{CHARLIT} {
5536 if (yyextra->insidePHP)
5537 {
5538 REJECT;
5539 }
5540 else
5541 {
5542 *yyextra->copyArgString+=yytext;
5543 yyextra->fullArgString+=yytext;
5544 }
5545 }
5546<ReadFuncArgType,ReadTempArgs,CopyArgRound,CopyArgSquare,CopyArgSharp>\' {
5547 *yyextra->copyArgString+=yytext;
5548 yyextra->fullArgString+=yytext;
5549 if (yyextra->insidePHP)
5550 {
5551 yyextra->lastCopyArgStringContext=YY_START;
5552 BEGIN(CopyArgPHPString);
5553 }
5554 }
5555<ReadFuncArgType,ReadTempArgs,CopyArgString,CopyArgPHPString,CopyArgRound,CopyArgSquare,CopyArgSharp>"<="|">="|"<=>" {
5556 *yyextra->copyArgString+=yytext;
5557 yyextra->fullArgString+=yytext;
5558 }
5559<ReadFuncArgType,ReadTempArgs,CopyArgString,CopyArgPHPString,CopyArgRound,CopyArgSquare,CopyArgSharp>\n {
5560 lineCount(yyscanner);
5561 *yyextra->copyArgString+=*yytext;
5562 yyextra->fullArgString+=*yytext;
5563 }
5564<ReadFuncArgType,ReadTempArgs,CopyArgString,CopyArgPHPString,CopyArgRound,CopyArgSquare,CopyArgSharp>{ID} {
5565 *yyextra->copyArgString+=yytext;
5566 yyextra->fullArgString+=yytext;
5567 }
5568<ReadFuncArgType,ReadTempArgs,CopyArgString,CopyArgPHPString,CopyArgRound,CopyArgSquare,CopyArgSharp>. {
5569 *yyextra->copyArgString+=*yytext;
5570 yyextra->fullArgString+=*yytext;
5571 }
5572
5573
5574
5575 /*------------------------------------------------------------------------*/
5576
5577
5578<FuncRound>"(" { yyextra->current->args += *yytext ;
5579 ++yyextra->roundCount ;
5580 }
5581<FuncRound>")" { yyextra->current->args += *yytext ;
5582 if ( yyextra->roundCount )
5583 --yyextra->roundCount ;
5584 else
5585 BEGIN( FuncQual ) ;
5586 }
5587 /*
5588<FuncQual>"#" { if (yyextra->insidePHP)
5589 REJECT;
5590 yyextra->lastCPPContext = YY_START;
5591 BEGIN(SkipCPP);
5592 }
5593 */
5594<FuncQual>[{:;,] {
5595 if ( dstrcmp(yytext,";")==0 &&
5596 ((yyextra->insideJS || yyextra->insidePHP) &&
5597 !yyextra->current->type.containsWord("function")) )
5598 {
5599 yyextra->current->reset();
5600 initEntry(yyscanner);
5601 BEGIN( FindMembers );
5602 }
5603 else
5604 {
5605 unput(*yytext); BEGIN( SFunction );
5606 }
5607 }
5608<FuncQual>{BN}*"abstract"{BN}* { // pure virtual member function
5609 lineCount(yyscanner) ;
5610 yyextra->current->virt = Specifier::Pure;
5611 yyextra->current->args += " override ";
5612 }
5613<FuncQual,TrailingReturn>{BN}*"override"{BN}* { // C++11 overridden virtual member function
5614 lineCount(yyscanner) ;
5615 yyextra->current->spec.setOverride(true);
5616 yyextra->current->args += " override ";
5617 if (YY_START==TrailingReturn) yyextra->current->argList.finishTrailingReturnType();
5618 BEGIN(FuncQual);
5619 }
5620<FuncQual,TrailingReturn>{BN}*"final"{BN}* { // C++11 final method
5621 lineCount(yyscanner) ;
5622 yyextra->current->spec.setFinal(true);
5623 yyextra->current->args += " final ";
5624 if (YY_START==TrailingReturn) yyextra->current->argList.finishTrailingReturnType();
5625 BEGIN(FuncQual);
5626 }
5627<FuncQual>{BN}*"sealed"{BN}* { // sealed member function
5628 lineCount(yyscanner) ;
5629 yyextra->current->spec.setSealed(true);
5630 yyextra->current->args += " sealed ";
5631 }
5632<FuncQual>{BN}*"new"{BN}* { // new member function
5633 lineCount(yyscanner) ;
5634 yyextra->current->spec.setNew(true);
5635 yyextra->current->args += " new ";
5636 }
5637<FuncQual>{BN}*"const"{BN}* { // const member function
5638 lineCount(yyscanner) ;
5639 yyextra->current->args += " const ";
5640 yyextra->current->argList.setConstSpecifier(true);
5641 }
5642<FuncQual>{BN}*"volatile"{BN}* { // volatile member function
5643 lineCount(yyscanner) ;
5644 yyextra->current->args += " volatile ";
5645 yyextra->current->argList.setVolatileSpecifier(true);
5646 }
5647<FuncQual>{BN}*"noexcept"{BN}* { // noexcept qualifier
5648 lineCount(yyscanner) ;
5649 yyextra->current->args += " noexcept ";
5650 yyextra->current->spec.setNoExcept(true);
5651 }
5652<FuncQual>{BN}*"noexcept"{BN}*"("{B}*false{B}*")"{BN}* { // noexcept(false) expression
5653 lineCount(yyscanner) ;
5654 yyextra->current->args += " noexcept(false)";
5655 }
5656<FuncQual>{BN}*"noexcept"{BN}*"(" { // noexcept expression
5657 lineCount(yyscanner) ;
5658 yyextra->current->args += " noexcept(";
5659 yyextra->current->spec.setNoExcept(true);
5660 yyextra->lastRoundContext=FuncQual;
5661 yyextra->pCopyRoundString=&yyextra->current->args;
5662 yyextra->roundCount=0;
5663 BEGIN(CopyRound);
5664 }
5665<FuncQual>{BN}*"&" {
5666 yyextra->current->args += " &";
5667 yyextra->current->argList.setRefQualifier(RefQualifierType::LValue);
5668 }
5669<FuncQual>{BN}*"&&" {
5670 yyextra->current->args += " &&";
5671 yyextra->current->argList.setRefQualifier(RefQualifierType::RValue);
5672 }
5673
5674<FuncQual,TrailingReturn>{BN}*"="{BN}*"0"{BN}* { // pure virtual member function
5675 lineCount(yyscanner) ;
5676 yyextra->current->args += " = 0";
5677 yyextra->current->virt = Specifier::Pure;
5678 yyextra->current->argList.setPureSpecifier(true);
5679 if (YY_START==TrailingReturn) yyextra->current->argList.finishTrailingReturnType();
5680 BEGIN(FuncQual);
5681 }
5682<FuncQual,TrailingReturn>{BN}*"="{BN}*"delete"{BN}* { // C++11 explicitly delete member
5683 lineCount(yyscanner);
5684 yyextra->current->args += " = delete";
5685 yyextra->current->spec.setDelete(true);
5686 yyextra->current->argList.setIsDeleted(true);
5687 if (YY_START==TrailingReturn) yyextra->current->argList.finishTrailingReturnType();
5688 BEGIN(FuncQual);
5689 }
5690<FuncQual,TrailingReturn>{BN}*"="{BN}*"default"{BN}* { // C++11 explicitly defaulted constructor/assignment operator
5691 lineCount(yyscanner);
5692 yyextra->current->args += " = default";
5693 yyextra->current->spec.setDefault(true);
5694 if (YY_START==TrailingReturn) yyextra->current->argList.finishTrailingReturnType();
5695 BEGIN(FuncQual);
5696 }
5697<FuncQual>{BN}*"->"{BN}* {
5698 lineCount(yyscanner);
5699 yyextra->current->argList.setTrailingReturnType(" -> ");
5700 yyextra->current->args += " -> ";
5701 yyextra->roundCount=0;
5702 BEGIN(TrailingReturn);
5703 }
5704<TrailingReturn>[{;] {
5705 if (yyextra->roundCount>0) REJECT;
5706 unput(*yytext);
5707 yyextra->current->argList.finishTrailingReturnType();
5708 BEGIN(FuncQual);
5709 }
5710<TrailingReturn>"requires"{BN}+ {
5711 if (yyextra->insideJava) REJECT;
5712 yyextra->requiresContext = FuncQual;
5713 yyextra->current->req+=' ';
5714 yyextra->current->argList.finishTrailingReturnType();
5715 BEGIN(RequiresClause);
5716 }
5717<TrailingReturn>"(" {
5718 yyextra->roundCount++;
5719 yyextra->current->argList.appendTrailingReturnType(yytext);
5720 yyextra->current->args+=yytext;
5721 }
5722<TrailingReturn>")" {
5723 if (yyextra->roundCount>0)
5724 {
5725 yyextra->roundCount--;
5726 }
5727 else
5728 {
5729 warn(yyextra->fileName,yyextra->yyLineNr,
5730 "Found ')' without opening '(' for trailing return type '{})...'",
5731 yyextra->current->argList.trailingReturnType());
5732 }
5733 yyextra->current->argList.appendTrailingReturnType(yytext);
5734 yyextra->current->args+=yytext;
5735 }
5736<TrailingReturn>. {
5737 yyextra->current->argList.appendTrailingReturnType(yytext);
5738 yyextra->current->args+=yytext;
5739 }
5740<TrailingReturn>\n {
5741 lineCount(yyscanner);
5742 yyextra->current->argList.appendTrailingReturnType(yytext);
5743 yyextra->current->args+=' ';
5744 }
5745<FuncRound,FuncFunc>{BN}*","{BN}* {
5746 lineCount(yyscanner) ;
5747 yyextra->current->args += ", " ;
5748 }
5749<FuncQual,FuncRound,FuncFunc>{BN}+ {
5750 lineCount(yyscanner) ;
5751 yyextra->current->args += ' ' ;
5752 }
5753<SFunction,FuncQual,FuncRound,FuncFunc>"#" { if (yyextra->insidePHP)
5754 REJECT;
5755 yyextra->lastCPPContext = YY_START;
5756 BEGIN(SkipCPP);
5757 }
5758<FuncQual>"=>" {
5759 if (!yyextra->insideCS)
5760 REJECT;
5761 // Expression body function
5762 unput('=');
5763 BEGIN(SFunction);
5764 }
5765<FuncQual>"=" {
5766 if (yyextra->insideCli && yyextra->current_root->section.isCompound())
5767 {
5768 BEGIN(CliOverride);
5769 }
5770 else
5771 {
5772 // typically an initialized function pointer
5773 yyextra->lastInitializerContext=YY_START;
5774 yyextra->sharpCount=0;
5775 yyextra->initBracketCount=0;
5776 yyextra->current->initializer.str(yytext);
5777 BEGIN(ReadInitializer);
5778 }
5779 }
5780<ReadExpressionBody>";" {
5781 if (!yyextra->current->sli.empty() && yyextra->previous) // copy special list items
5782 {
5783 yyextra->previous->sli = yyextra->current->sli;
5784 yyextra->current->sli.clear();
5785 }
5786 if (yyextra->previous) yyextra->previous->endBodyLine=yyextra->yyLineNr;
5787 BEGIN(FindMembers);
5788 }
5789<CliOverride>{ID} {
5790 }
5791<CliOverride>"{" {
5792 unput(*yytext);
5793 BEGIN(FuncQual);
5794 }
5795<CliOverride>\n {
5796 lineCount(yyscanner);
5797 }
5798<CliOverride>. {
5799 }
5800<FuncQual>{ID} {
5801 if (yyextra->insideCpp && dstrcmp(yytext,"requires")==0)
5802 {
5803 // c++20 trailing requires clause
5804 yyextra->requiresContext = YY_START;
5805 if (!yyextra->current->req.empty())
5806 {
5807 yyextra->current->req+=" && ";
5808 }
5809 BEGIN(RequiresClause);
5810 }
5811 else if (yyextra->insideCS && dstrcmp(yytext,"where")==0)
5812 {
5813 // type constraint for a method
5814 yyextra->current->typeConstr.clear();
5815 yyextra->current->typeConstr.push_back(Argument());
5816 yyextra->lastCSConstraint = YY_START;
5817 BEGIN( CSConstraintName );
5818 }
5819 else if (checkForKnRstyleC(yyscanner)) // K&R style C function
5820 {
5821 yyextra->current->args = yytext;
5822 yyextra->oldStyleArgType.clear();
5823 BEGIN(OldStyleArgs);
5824 }
5825 else
5826 {
5827 yyextra->current->args += yytext;
5828 }
5829 }
5830<OldStyleArgs>[,;] {
5831 DString oldStyleArgPtr;
5832 DString oldStyleArgName;
5833 splitKnRArg(yyscanner,oldStyleArgPtr,oldStyleArgName);
5834 DString doc,brief;
5835 if (yyextra->current->doc!=yyextra->docBackup)
5836 {
5837 doc=yyextra->current->doc;
5838 yyextra->current->doc=yyextra->docBackup;
5839 }
5840 if (yyextra->current->brief!=yyextra->briefBackup)
5841 {
5842 brief=yyextra->current->brief;
5843 yyextra->current->brief=yyextra->briefBackup;
5844 }
5845 addKnRArgInfo(yyscanner,yyextra->oldStyleArgType+oldStyleArgPtr,
5846 oldStyleArgName,brief,doc);
5847 yyextra->current->args.clear();
5848 if (*yytext==';') yyextra->oldStyleArgType.clear();
5849 }
5850<OldStyleArgs>{ID} { yyextra->current->args += yytext; }
5851<OldStyleArgs>"{" {
5852 if (yyextra->current->argList.empty())
5853 {
5854 yyextra->current->argList.setNoParameters(true);
5855 }
5856 yyextra->current->args = argListToString(yyextra->current->argList);
5857 unput('{');
5858 BEGIN(FuncQual);
5859 }
5860<OldStyleArgs>. { yyextra->current->args += *yytext; }
5861<FuncQual,FuncRound,FuncFunc>\" {
5862 if (yyextra->insideIDL && yyextra->insideCppQuote)
5863 {
5864 BEGIN(EndCppQuote);
5865 }
5866 else
5867 {
5868 yyextra->current->args += *yytext;
5869 }
5870 }
5871<FuncQual,FuncRound,FuncFunc>. { yyextra->current->args += *yytext; }
5872<FuncQual>{BN}*"try:" |
5873<FuncQual>{BN}*"try"{BN}+ { /* try-function-block */
5874 yyextra->insideTryBlock=true;
5875 lineCount(yyscanner);
5876 if (yytext[yyleng-1]==':')
5877 {
5878 unput(':');
5879 BEGIN( SFunction );
5880 }
5881 }
5882<FuncQual>{BN}*"throw"{BN}*"(" { // C++ style throw clause
5883 yyextra->current->exception = " throw (" ;
5884 yyextra->roundCount=0;
5885 lineCount(yyscanner) ;
5886 BEGIN( ExcpRound ) ;
5887 }
5888<FuncQual>{BN}*"raises"{BN}*"(" {
5889 yyextra->current->exception = " raises (" ;
5890 lineCount(yyscanner) ;
5891 yyextra->roundCount=0;
5892 BEGIN( ExcpRound ) ;
5893 }
5894<FuncQual>{BN}*"throws"{BN}+ { // Java style throw clause
5895 yyextra->current->exception = " throws " ;
5896 lineCount(yyscanner) ;
5897 BEGIN( ExcpList );
5898 }
5899<ExcpRound>"(" { yyextra->current->exception += *yytext ;
5900 ++yyextra->roundCount ;
5901 }
5902<ExcpRound>")" { yyextra->current->exception += *yytext ;
5903 if ( yyextra->roundCount )
5904 --yyextra->roundCount ;
5905 else
5906 BEGIN( FuncQual ) ;
5907 }
5908<ExcpRound>. {
5909 yyextra->current->exception += *yytext;
5910 }
5911<ExcpList>"{" {
5912 unput('{'); BEGIN( FuncQual );
5913 }
5914<ExcpList>";" {
5915 unput(';'); BEGIN( FuncQual );
5916 }
5917<ExcpList>"\n" {
5918 yyextra->current->exception += ' ';
5919 lineCount(yyscanner);
5920 }
5921<ExcpList>. {
5922 yyextra->current->exception += *yytext;
5923 }
5924<SFunction>"(" { yyextra->current->type += yyextra->current->name ;
5925 yyextra->current->name = yyextra->current->args ;
5926 yyextra->current->args = yytext ;
5927 yyextra->roundCount=0;
5928 BEGIN( FuncRound ) ;
5929 }
5930<SFunction>":" {
5931 if (!yyextra->insidePHP) BEGIN(SkipInits);
5932 }
5933<SFunction>[=;{,] {
5934 yyextra->current->name=removeRedundantWhiteSpace(yyextra->current->name);
5935 yyextra->current->type=removeRedundantWhiteSpace(yyextra->current->type);
5936 yyextra->current->args=removeRedundantWhiteSpace(yyextra->current->args);
5937 yyextra->current->fileName = yyextra->fileName;
5938 yyextra->current->startLine = yyextra->yyBegLineNr;
5939 yyextra->current->startColumn = yyextra->yyBegColNr;
5940 static const reg::Ex re(R"(\‍([^)]*[*&][^)]*\))"); // e.g. (...*...)
5942 std::string type = yyextra->current->type.str();
5943 size_t ti=DString::npos;
5944 if (reg::search(type,match,re))
5945 {
5946 ti = match.position();
5947 }
5948 if (ti!=DString::npos)
5949 {
5950 if (size_t di = yyextra->current->type.find("decltype(");
5951 di!=DString::npos && di<ti) // decltype(...(...*...) -> normal return type
5952 {
5953 ti = DString::npos;
5954 }
5955 }
5956 size_t ts=yyextra->current->type.find('<');
5957 size_t te=yyextra->current->type.rfind('>');
5958
5959 // bug677315: A<int(void *, char *)> get(); is not a function pointer
5960 bool startsWithTypedef = yyextra->current->type.startsWith("typedef ");
5961 bool isFunction = ti==DString::npos || // not a (...*...) pattern
5962 (ts!=DString::npos && te!=DString::npos && ts<te && ts<ti && ti<te); // (...*...) is part of a template argument list
5963 bool isVariable = !yyextra->current->type.empty() &&
5964 (!isFunction || startsWithTypedef);
5965
5966 //printf("type=%s ts=%d te=%d ti=%d isFunction=%d\n",
5967 // qPrint(yyextra->current->type),ts,te,ti,isFunction);
5968
5969 if (*yytext!=';' || yyextra->current_root->section.isCompound())
5970 {
5971 if (isVariable)
5972 {
5973 //printf("Scanner.l: found in class variable: '%s' '%s' '%s'\n", qPrint(yyextra->current->type),qPrint(yyextra->current->name),qPrint(yyextra->current->args));
5974 if (yyextra->isTypedef && !startsWithTypedef)
5975 {
5976 yyextra->current->type.prepend("typedef ");
5977 }
5978 yyextra->current->section = EntryType::makeVariable() ;
5979 }
5980 else
5981 {
5982 //printf("Scanner.l: found in class function: '%s' '%s' '%s'\n", qPrint(yyextra->current->type),qPrint(yyextra->current->name),qPrint(yyextra->current->args));
5983 yyextra->current->section = EntryType::makeFunction() ;
5984 yyextra->current->proto = *yytext==';';
5985 }
5986 }
5987 else // a global function prototype or function variable
5988 {
5989 //printf("Scanner.l: prototype? type='%s' name='%s' args='%s'\n",qPrint(yyextra->current->type),qPrint(yyextra->current->name),qPrint(yyextra->current->args));
5990 if (isVariable)
5991 {
5992 if (yyextra->isTypedef && !startsWithTypedef)
5993 {
5994 yyextra->current->type.prepend("typedef ");
5995 }
5996 //printf("Scanner.l: found function variable!\n");
5997 yyextra->current->section = EntryType::makeVariable();
5998 }
5999 else
6000 {
6001 //printf("Scanner.l: found prototype\n");
6002 yyextra->current->section = EntryType::makeFunction();
6003 yyextra->current->proto = true;
6004 }
6005 }
6006 //printf("Adding entry '%s'\n",qPrint(yyextra->current->name));
6007 if ( yyextra->insidePHP)
6008 {
6009 if (yyextra->current->type.findAndRemoveWord("final"))
6010 {
6011 yyextra->current->spec.setFinal(true);
6012 }
6013 if (yyextra->current->type.findAndRemoveWord("abstract"))
6014 {
6015 yyextra->current->spec.setAbstract(true);
6016 }
6017 }
6018 if ( yyextra->insidePHP && !yyextra->current->type.containsWord("function"))
6019 {
6020 initEntry(yyscanner);
6021 if ( *yytext == '{' )
6022 {
6023 yyextra->lastCurlyContext = FindMembers;
6024 yyextra->curlyCount=0;
6025 BEGIN( SkipCurly );
6026 }
6027 else
6028 {
6029 BEGIN( FindMembers );
6030 }
6031 }
6032 else
6033 {
6034 if ( yyextra->insidePHP)
6035 {
6036 yyextra->current->type.findAndRemoveWord("function");
6037 }
6038 yyextra->previous = yyextra->current;
6039 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
6040 initEntry(yyscanner);
6041 // Objective C 2.0: Required/Optional section
6042 if (yyextra->previous->spec.isOptional() || yyextra->previous->spec.isRequired())
6043 {
6044 yyextra->current->spec.setOptional(true).setRequired(true);
6045 }
6046 yyextra->lastCurlyContext = FindMembers;
6047 if ( *yytext == ',' )
6048 {
6049 yyextra->current->type = stripFuncPtr(yyextra->previous->type);
6050 }
6051 if ( *yytext == '{' )
6052 {
6053 if ( !yyextra->insidePHP && yyextra->current_root->section.isCompound() )
6054 {
6055 yyextra->previous->spec.setInline(true);
6056 }
6057 yyextra->curlyCount=0;
6058 BEGIN( SkipCurly ) ;
6059 }
6060 else if ( *yytext == '=' ) // C# Expression Body
6061 {
6062 yyextra->previous->spec.setInline(true);
6063 yyextra->curlyCount=0;
6064 BEGIN( ReadExpressionBody );
6065 }
6066 else
6067 {
6068 if (!yyextra->previous->section.isVariable())
6069 yyextra->previous->bodyLine=-1; // a function/member declaration
6070 BEGIN( FindMembers ) ;
6071 }
6072 }
6073 }
Class representing a regular expression.
Definition regex.h:39
Object representing the matching results.
Definition regex.h:154
bool search(std::string_view str, Match &match, const Ex &re, size_t pos)
Search in a given string str starting at position pos for a match against regular expression re.
Definition regex.cpp:850
bool match(std::string_view str, Match &match, const Ex &re)
Matches a given string str for a match against regular expression re.
Definition regex.cpp:861
6074<SkipInits>">"{BN}*"{" { // C++11 style initializer (see bug 790788)
6075 lineCount(yyscanner);
6076 yyextra->curlyCount=1;
6077 BEGIN(SkipC11Inits);
6078 }
6079<SkipInits>{ID}{BN}*"{" { // C++11 style initializer (see bug 688647)
6080 lineCount(yyscanner);
6081 yyextra->curlyCount=1;
6082 BEGIN(SkipC11Inits);
6083 }
6084<SkipC11Inits>"{" {
6085 ++yyextra->curlyCount;
6086 }
6087<SkipC11Inits>"}" {
6088 if ( --yyextra->curlyCount<=0 )
6089 {
6090 BEGIN(SkipInits);
6091 }
6092 }
6093<SkipInits>"{" { // C++11 style initializer
6094 unput('{');
6095 BEGIN( SFunction );
6096 }
6097<SkipCurly>"{" {
6098 //addToBody(yytext);
6099 ++yyextra->curlyCount ;
6100 }
6101<SkipCurly>"}"/{BN}*{DCOMM}"<!--" | /* see bug710917 */)
6102<SkipCurly>"}" {
6103 //addToBody(yytext);
6104 if( yyextra->curlyCount )
6105 {
6106 --yyextra->curlyCount ;
6107 }
6108 else
6109 {
6110 if (!yyextra->current->sli.empty() && yyextra->previous) // copy special list items
6111 {
6112 yyextra->previous->sli = yyextra->current->sli;
6113 yyextra->current->sli.clear();
6114 }
6115 if (yyextra->previous) yyextra->previous->endBodyLine=yyextra->yyLineNr;
6116 BEGIN( yyextra->lastCurlyContext ) ;
6117 }
6118 }
6119<SkipCurly>"}"{BN}*{DCOMM}"<" {
6120 lineCount(yyscanner);
6121 if ( yyextra->curlyCount )
6122 {
6123 //addToBody(yytext);
6124 --yyextra->curlyCount ;
6125 }
6126 else
6127 {
6128 yyextra->current->endBodyLine=yyextra->yyLineNr;
6129 yyextra->tempEntry = yyextra->current; // temporarily switch to the previous entry
6130 yyextra->current = yyextra->previous;
6131
6132 yyextra->docBlockContext = SkipCurlyEndDoc;
6133 yyextra->docBlockInBody = false;
6134 yyextra->docBlockAutoBrief = ( yytext[yyleng-2]=='*' && Config_getBool(JAVADOC_AUTOBRIEF) ) ||
6135 ( yytext[yyleng-2]=='!' && Config_getBool(QT_AUTOBRIEF) );
6136 yyextra->docBlock.str(std::string());
6137 yyextra->docBlockTerm = '}';
6138 if (yytext[yyleng-3]=='/')
6139 {
6140 startCommentBlock(yyscanner,true);
6141 BEGIN( DocLine );
6142 }
6143 else
6144 {
6145 startCommentBlock(yyscanner,false);
6146 BEGIN( DocBlock );
6147 }
6148 }
6149 }
6150<SkipCurlyEndDoc>"}"{BN}*{DCOMM}"<" { // desc is followed by another one
6151 yyextra->docBlockContext = SkipCurlyEndDoc;
6152 yyextra->docBlockInBody = false;
6153 yyextra->docBlockAutoBrief = ( yytext[yyleng-2]=='*' && Config_getBool(JAVADOC_AUTOBRIEF) ) ||
6154 ( yytext[yyleng-2]=='!' && Config_getBool(QT_AUTOBRIEF) );
6155 yyextra->docBlock.str(std::string());
6156 yyextra->docBlockTerm = '}';
6157 if (yytext[yyleng-3]=='/')
6158 {
6159 startCommentBlock(yyscanner,true);
6160 BEGIN( DocLine );
6161 }
6162 else
6163 {
6164 startCommentBlock(yyscanner,false);
6165 BEGIN( DocBlock );
6166 }
6167 }
6168<SkipCurlyEndDoc>"}" {
6169 //addToBody("}");
6170 if (yyextra->tempEntry) // we can only switch back to yyextra->current if no new item was created
6171 {
6172 yyextra->current = yyextra->tempEntry;
6173 yyextra->tempEntry.reset();
6174 }
6175 BEGIN( yyextra->lastCurlyContext );
6176 }
6177<SkipCurly,ReadExpressionBody>\" {
6178 //addToBody(yytext);
6179 yyextra->lastStringContext=YY_START;
6180 BEGIN( SkipString );
6181 }
6182<SkipCurly>^{B}*"#" {
6183 if (yyextra->insidePHP)
6184 REJECT;
6185 //addToBody(yytext);
6186 BEGIN( SkipCurlyCpp );
6187 }
6188<SkipCurly,SkipC11Inits,SkipInits,ReadExpressionBody>\n {
6189 lineCount(yyscanner);
6190 //addToBody(yytext);
6191 }
6192<SkipCurly,SkipCurlyCpp,ReadInitializer,ReadInitializerPtr>"<<<" {
6193 if (!yyextra->insidePHP)
6194 {
6195 REJECT;
6196 }
6197 else
6198 {
6199 yyextra->lastHereDocContext = YY_START;
6200 BEGIN(HereDoc);
6201 }
6202 }
6203<SkipCurly,SkipCurlyCpp>{B}*{RAWBEGIN} {
6204 yyextra->delimiter = extractBeginRawStringDelimiter(yytext);
6205 yyextra->lastRawStringContext = YY_START;
6206 yyextra->dummyRawString.clear();
6207 yyextra->pCopyRawString = &yyextra->dummyRawString;
6208 *yyextra->pCopyRawString += yytext;
6209 BEGIN(RawString);
6210 }
6211<SkipCurly,SkipCurlyCpp>[^\n#"R'@\\/{}<\$]+ {
6212 lineCount(yyscanner); // for yyextra->column updates
6213 //addToBody(yytext);
6214 }
6215<SkipCurly,SkipCurlyCpp>"\$" {}
6216<SkipCurlyCpp>\n {
6217 //addToBody(yytext);
6218 lineCount(yyscanner);
6219 yyextra->lastCurlyContext = FindMembers;
6220 BEGIN( SkipCurly );
6221 }
6222<SkipCurlyCpp>\\‍[\r]*"\n"[\r]* {
6223 //addToBody(yytext);
6224 lineCount(yyscanner);
6225 }
6226<SkipInits,SkipC11Inits,SkipCurly,SkipCurlyCpp,CopyC11Attribute,ReadExpressionBody>{CCS} {
6227 //addToBody(yytext);
6228 yyextra->lastCContext = YY_START;
6229 BEGIN(SkipComment);
6230 }
6231<SkipInits,SkipC11Inits,SkipCurly,SkipCurlyCpp,CopyC11Attribute,ReadExpressionBody>{CPPC} {
6232 //addToBody(yytext);
6233 yyextra->lastCContext = YY_START;
6234 BEGIN(SkipCxxComment);
6235 }
6236<SkipInits,SkipC11Inits>"(" {
6237 yyextra->roundCount=0;
6238 yyextra->lastSkipRoundContext=YY_START;
6239 BEGIN(SkipRound);
6240 }
6241<SkipInits,SkipC11Inits>\" {
6242 yyextra->lastStringContext=YY_START;
6243 BEGIN( SkipString );
6244 }
6245<SkipInits>; {
6246 warn(yyextra->fileName,yyextra->yyLineNr,
6247 "Found ';' while parsing initializer list! "
6248 "(doxygen could be confused by a macro call without semicolon)"
6249 );
6250 BEGIN( FindMembers );
6251 }
6252<SkipInits,SkipCurly,SkipCurlyCpp>"#" {
6253 if (!yyextra->insidePHP)
6254 REJECT;
6255 //addToBody(yytext);
6256 yyextra->lastCContext = YY_START;
6257 BEGIN(SkipCxxComment);
6258 }
6259<SkipInits,SkipCurly,SkipCurlyCpp,ReadExpressionBody>@\" {
6260 if (!yyextra->insideCS) REJECT;
6261 // C# verbatim string
6262 // we want to discard the string, due to reuse of states we need a dummy stream
6263 yyextra->lastSkipVerbStringContext=YY_START;
6264 yyextra->pSkipVerbString=&yyextra->dummyTextStream;
6265 yyextra->dummyTextStream.clear(); // remove old data so it won't grow too much
6266 BEGIN(SkipVerbString);
6267 }
6268<SkipInits,SkipCurly,SkipCurlyCpp,ReadExpressionBody>{CHARLIT} {
6269 if (yyextra->insidePHP) REJECT;
6270 }
6271<SkipInits,SkipCurly,SkipCurlyCpp>\' {
6272 if (yyextra->insidePHP)
6273 {
6274 yyextra->lastStringContext=YY_START;
6275 BEGIN(SkipPHPString);
6276 }
6277 }
6278<SkipInits,SkipC11Inits,SkipCurly,SkipCurlyCpp,ReadExpressionBody>. { }
6279<SkipString,SkipPHPString>\\. { }
6280<SkipString>\" {
6281 BEGIN( yyextra->lastStringContext );
6282 }
6283<SkipPHPString>\' {
6284 BEGIN( yyextra->lastStringContext );
6285 }
6286<SkipString,SkipPHPString>{CCS}|{CCE}|{CPPC} { }
6287<SkipString,SkipPHPString>\n {
6288 lineCount(yyscanner);
6289 }
6290<SkipString>"[[" { }
6291<SkipString,SkipPHPString>. { }
6292<CompoundName>":" { // for "class : public base {} var;" construct, see bug 608359
6293 unput(':');
6294 BEGIN(ClassVar);
6295 }
6296<CompoundName>";" {
6297 yyextra->current->section = EntryType::makeEmpty() ;
6298 yyextra->current->type.clear() ;
6299 yyextra->current->name.clear() ;
6300 yyextra->current->args.clear() ;
6301 yyextra->current->argList.clear();
6302 BEGIN( FindMembers ) ;
6303 }
6304<Bases>";" {
6305 if (yyextra->insideIDL && (yyextra->current->spec.isSingleton() || yyextra->current->spec.isService()))
6306 {
6307 // in UNO IDL a service or singleton may be defined
6308 // completely like this: "service Foo : XFoo;"
6309 if (!yyextra->current->name.empty() && !yyextra->current_root->name.empty())
6310 {
6311 prependScope(yyscanner);
6312 }
6313 yyextra->current->name = yyextra->current->name.stripWhiteSpace();
6314 // there can be only one base class here
6315 if (!yyextra->baseName.empty())
6316 {
6317 yyextra->current->extends.emplace_back(
6318 yyextra->baseName,Protection::Public,Specifier::Normal);
6319 yyextra->baseName.clear();
6320 }
6321 yyextra->current_root->moveToSubEntryAndRefresh( yyextra->current ) ;
6322 initEntry(yyscanner);
6323 }
6324 else
6325 {
6326 yyextra->current->section = EntryType::makeEmpty() ;
6327 yyextra->current->type.clear() ;
6328 yyextra->current->name.clear() ;
6329 yyextra->current->args.clear() ;
6330 yyextra->current->argList.clear();
6331 }
6332 BEGIN( FindMembers ) ;
6333 }
6334<CompoundName>{SCOPENAME}/{BN}*"<" {
6335 yyextra->sharpCount = 0;
6336 yyextra->current->name = yytext ;
6337 storeClangId(yyscanner,yytext);
6338 if (yyextra->current->spec.isProtocol())
6339 {
6340 yyextra->current->name+="-p";
6341 }
6342 lineCount(yyscanner);
6343 yyextra->lastClassTemplSpecContext = ClassVar;
6344 if (yyextra->insideObjC) // protocol list
6345 {
6346 BEGIN( ObjCProtocolList );
6347 }
6348 else if (yyextra->insideCS) // C# generic class
6349 {
6350 //yyextra->current->name+="-g";
6351 BEGIN( CSGeneric );
6352 }
6353 else // C++ template specialization
6354 {
6355 yyextra->roundCount=0;
6356 BEGIN( ClassTemplSpec );
6357 }
6358 }
6359<CSGeneric>"<" {
6360 ArgumentList al;
6361 // check bug 612858 before enabling the next line
6362 //yyextra->current->spec |= Entry::Template;
6363 yyextra->current->tArgLists.push_back(al);
6364 yyextra->currentArgumentList = &yyextra->current->tArgLists.back();
6365 yyextra->templateStr="<";
6366 yyextra->current->name += "<";
6367 yyextra->fullArgString = yyextra->templateStr;
6368 yyextra->copyArgString = &yyextra->current->name;
6369 //yyextra->copyArgString = &yyextra->templateStr;
6370 yyextra->currentArgumentContext = ClassVar;
6371 BEGIN( ReadTempArgs );
6372 }
6373<ObjCProtocolList>"<" {
6374 yyextra->insideProtocolList=true;
6375 BEGIN( Bases );
6376 }
6377<ClassTemplSpec>">"({BN}*"::"{BN}*{SCOPENAME})? {
6378 yyextra->current->name += yytext;
6379 lineCount(yyscanner);
6380 if (yyextra->roundCount==0 && --yyextra->sharpCount<=0)
6381 {
6382 yyextra->current->name = removeRedundantWhiteSpace(yyextra->current->name);
6383 if (yyextra->current->spec.isProtocol())
6384 { // Objective-C protocol
6385 unput('{'); // fake start of body
6386 BEGIN( ClassVar );
6387 }
6388 else
6389 {
6390 BEGIN( yyextra->lastClassTemplSpecContext );
6391 }
6392 }
6393 }
6394<ClassTemplSpec>"<" {
6395 yyextra->current->name += yytext;
6396 if (yyextra->roundCount==0) yyextra->sharpCount++;
6397 }
6398<ClassTemplSpec>. {
6399 yyextra->current->name += yytext;
6400 }
6401<CompoundName>({SCOPENAME}|{CSSCOPENAME}){BN}*";" { // forward declaration?
6402 if (yyextra->insideCS && yyextra->current->type == "namespace")
6403 {
6404 // file scoped CSharp namespace
6405 lineCount(yyscanner);
6406 yyextra->current->name = substitute(yytext,".","::");
6407 yyextra->current->name=yyextra->current->name.left(yyextra->current->name.length()-1).stripWhiteSpace();
6408 yyextra->fakeNS++;
6409 unput('{'); // fake start of body
6410 BEGIN( ClassVar );
6411 }
6412 else if (!yyextra->current->tArgLists.empty())
6413 {
6414 // found a forward template declaration, this has
6415 // a purpose of its own
6416 yyextra->current->name = yytext;
6417 yyextra->current->name=yyextra->current->name.left(yyextra->current->name.length()-1).stripWhiteSpace();
6418 storeClangId(yyscanner,yyextra->current->name.data());
6419 //printf("template class declaration for %s!\n",qPrint(yyextra->current->name));
6420 DString rn = yyextra->current_root->name;
6421 //printf("cn='%s' rn='%s' yyextra->isTypedef=%d\n",qPrint(cn),qPrint(rn),yyextra->isTypedef);
6422 if (!yyextra->current->name.empty() && !rn.empty())
6423 {
6424 prependScope(yyscanner);
6425 }
6426 yyextra->current->spec.setForwardDecl(true);
6427 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
6428 }
6429 else if (yyextra->insideIDL &&
6430 (((yyextra->current_root->spec.isInterface() || yyextra->current_root->spec.isService()) &&
6431 yyextra->current->spec.isInterface()) ||
6432 ((yyextra->current_root->spec.isService() || yyextra->current_root->spec.isSingleton()) &&
6433 yyextra->current->spec.isService())
6434 )
6435 )
6436 {
6437 // interface yyextra->inside of UNO IDL service or interface
6438 // service yyextra->inside of UNO IDL service or singleton
6439 // there may be documentation on the member,
6440 // so do not throw it away...
6441 yyextra->current->name = yytext;
6442 yyextra->current->name=yyextra->current->name.left(yyextra->current->name.length()-1).stripWhiteSpace();
6443 yyextra->current->section = yyextra->current->spec.isInterface() ? EntryType::makeExportedInterface()
6444 : EntryType::makeIncludedService();
6445// yyextra->current->section = EntryType::makeMemberDoc();
6446 yyextra->current->spec.setInterface(false).setService(false);
6447 // FIXME: horrible: Interface == Gettable, so need to clear it - actually we're mixing values from
6448 // different enums in this case...
6449 // granted only Optional and Interface are actually valid in this context but urgh...
6450 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
6451 }
6452
6453 if (!(yyextra->insideCS && yyextra->current->type == "namespace"))
6454 {
6455 unput(';');
6456 yyextra->current->reset();
6457 initEntry(yyscanner);
6458 if (yyextra->insideObjC) // see bug746361
6459 {
6460 yyextra->language = yyextra->current->lang = SrcLangExt::Cpp;
6461 yyextra->insideObjC = false;
6462 }
6463 if (yyextra->isTypedef) // typedef of a class, put typedef keyword back
6464 {
6465 yyextra->current->type.prepend("typedef");
6466 }
6467 BEGIN( FindMembers );
6468 }
6469 }
Wrapper class for the Entry type.
Definition types.h:856
6470<CompoundName>{SCOPENAME}/{BN}*"(" {
6471 yyextra->current->name = yytext ;
6472 storeClangId(yyscanner,yytext);
6473 lineCount(yyscanner);
6474 if (yyextra->insideCpp && yyextra->current->name=="alignas") // C++11
6475 {
6476 yyextra->lastAlignAsContext = YY_START;
6477 BEGIN( AlignAs );
6478 }
6479 else
6480 {
6481 if (yyextra->current->spec.isProtocol())
6482 {
6483 yyextra->current->name += "-p";
6484 }
6485 BEGIN( ClassVar );
6486 }
6487 }
6488<AlignAs>"(" { yyextra->roundCount=0;
6489 BEGIN( AlignAsEnd );
6490 }
6491<AlignAs>\n { lineCount(yyscanner); }
6492<AlignAs>.
6493<AlignAsEnd>"(" { yyextra->roundCount++; }
6494<AlignAsEnd>")" { if (--yyextra->roundCount<0)
6495 {
6496 BEGIN( yyextra->lastAlignAsContext );
6497 }
6498 }
6499<AlignAsEnd>\n { lineCount(yyscanner); }
6500<AlignAsEnd>.
6501<ConceptName>{ID} {
6502 yyextra->current->name = yytext ;
6503 storeClangId(yyscanner,yytext);
6504 }
6505<ConceptName>"=" {
6506 yyextra->current->bodyLine = yyextra->yyLineNr;
6507 yyextra->current->bodyColumn = yyextra->yyColNr;
6508 yyextra->current->initializer.str(std::string());
6509 yyextra->lastInitializerContext = FindMembers;
6510 yyextra->sharpCount=0;
6511 yyextra->initBracketCount=0;
6512 BEGIN(ReadInitializer);
6513 }
6514<CompoundName>{SCOPENAME}/{BN}*"," { // multiple forward declarations on one line
6515 // e.g. @protocol A,B;
6516 yyextra->current->reset();
6517 initEntry(yyscanner);
6518 }
6519<CompoundName>{SCOPENAME} {
6520 yyextra->current->name = yytext ;
6521 storeClangId(yyscanner,yytext);
6522 lineCount(yyscanner);
6523 if (yyextra->current->spec.isProtocol())
6524 {
6525 yyextra->current->name += "-p";
6526 }
6527 if (yyextra->current->spec.isProtocol() || yyextra->current->section.isObjcImpl())
6528 {
6529 unput('{'); // fake start of body
6530 }
6531 BEGIN( ClassVar );
6532 }
6533<CompoundName>({ID}{BN}*"::"{BN}*)+("inline"{BN}+({ID}{BN}*"::"{BN}*)*)+{ID} { // C++20 style nested inline namespace syntax
6534 if (yyextra->current->section.isNamespace())
6535 {
6536 yyextra->current->name = DString(yytext).simplifyWhiteSpace();
6537 storeClangId(yyscanner,yyextra->current->name.data());
6538 lineCount(yyscanner);
6539 BEGIN( ClassVar );
6540 }
6541 else
6542 {
6543 REJECT;
6544 }
6545 }
DString simplifyWhiteSpace() const
return a copy of this string with leading and trailing whitespace removed and multiple internal white...
Definition dstring.cpp:127
6546<CompoundName>{CSSCOPENAME} { // C# style scope
6547 yyextra->current->name = substitute(yytext,".","::");
6548 lineCount(yyscanner);
6549 BEGIN( ClassVar );
6550 }
6551<ClassVar>{SCOPENAME}{BNopt}/"(" {
6552 if (yyextra->insideIDL && literal_at(yytext,"switch") && !isId(yytext[6]))
6553 {
6554 // Corba IDL style union
6555 yyextra->roundCount=0;
6556 BEGIN(SkipUnionSwitch);
6557 }
6558 else
6559 {
6560 addType(yyscanner);
6561 yyextra->yyBegColNr=yyextra->yyColNr;
6562 yyextra->yyBegLineNr=yyextra->yyLineNr;
6563 yyextra->current->name = yytext;
6564 yyextra->current->name = yyextra->current->name.stripWhiteSpace();
6565 storeClangId(yyscanner,yyextra->current->name.data());
6566 lineCount(yyscanner);
6567 BEGIN( FindMembers );
6568 }
6569 }
6570<ClassVar>"," {
6571 if (yyextra->isTypedef)
6572 {
6573 // multiple types in one typedef
6574 unput(',');
6575 yyextra->current->type.prepend("typedef ");
6576 BEGIN(FindMembers);
6577 }
6578 else
6579 {
6580 // Multiple class forward declaration
6581 }
6582 }
6583<ClassVar>("sealed"|"abstract")/{BN}*(":"|"{") {
6584 if (yyextra->insideCli)
6585 {
6586 if (yytext[0]=='s') // sealed
6587 yyextra->current->spec.setSealedClass(true);
6588 else // abstract
6589 yyextra->current->spec.setAbstractClass(true);
6590 BEGIN( ClassVar );
6591 }
6592 else
6593 {
6594 REJECT;
6595 }
6596 }
6597<ClassVar>({ID}{BN}*"::"{BN}*)+{ID} {
6598 yyextra->yyBegColNr=yyextra->yyColNr;
6599 yyextra->yyBegLineNr=yyextra->yyLineNr;
6600 storeClangId(yyscanner,yytext);
6601 lineCount(yyscanner);
6602 if (yyextra->current->section.isEnum())
6603 { // found "enum a N::b" -> variable
6604 yyextra->current->section = EntryType::makeVariable() ;
6605 }
6606 yyextra->current->type += ' ' ;
6607 yyextra->current->type += yyextra->current->name ;
6608 yyextra->current->name = DString(yytext).simplifyWhiteSpace();
6609
6610 if (nameIsOperator(yyextra->current->name))
6611 {
6612 BEGIN( Operator );
6613 }
6614 }
6615<ClassVar>{ID} {
6616 yyextra->yyBegColNr=yyextra->yyColNr;
6617 yyextra->yyBegLineNr=yyextra->yyLineNr;
6618 storeClangId(yyscanner,yytext);
6619 if (yyextra->insideIDL && dstrcmp(yytext,"switch")==0)
6620 {
6621 // Corba IDL style union
6622 yyextra->roundCount=0;
6623 BEGIN(SkipUnionSwitch);
6624 }
6625 else if ((yyextra->insideJava || yyextra->insidePHP || yyextra->insideJS || yyextra->insideSlice) && (dstrcmp(yytext,"implements")==0 || dstrcmp(yytext,"extends")==0))
6626 {
6627 yyextra->current->type.clear();
6628 yyextra->baseProt = Protection::Public;
6629 yyextra->baseVirt = Specifier::Normal;
6630 yyextra->baseName.clear();
6631 BEGIN( BasesProt ) ;
6632 }
6633 else if (yyextra->insideCS && dstrcmp(yytext,"where")==0) // C# type constraint
6634 {
6635 yyextra->current->typeConstr.clear();
6636 yyextra->current->typeConstr.push_back(Argument());
6637 yyextra->lastCSConstraint = YY_START;
6638 BEGIN( CSConstraintName );
6639 }
6640 else if (yyextra->insideCli && dstrcmp(yytext,"abstract")==0)
6641 {
6642 yyextra->current->spec.setAbstract(true);
6643 }
6644 else if (yyextra->insideCli && dstrcmp(yytext,"sealed")==0)
6645 {
6646 yyextra->current->spec.setSealed(true);
6647 }
6648 else if (dstrcmp(yytext,"final")==0)
6649 {
6650 yyextra->current->spec.setFinal(true);
6651 }
6652 else
6653 {
6654 if (yyextra->current->section.isEnum())
6655 { // found "enum a b" -> variable
6656 yyextra->current->section = EntryType::makeVariable() ;
6657 }
6658 yyextra->current->type += ' ' ;
6659 yyextra->current->type += yyextra->current->name ;
6660 yyextra->current->name = yytext ;
6661
6662 if (nameIsOperator(yyextra->current->name))
6663 {
6664 BEGIN( Operator );
6665 }
6666 }
6667 }
6668<ClassVar>[(\‍[] {
6669 if (yyextra->insideObjC && *yytext=='(') // class category
6670 {
6671 yyextra->current->name+='(';
6672 yyextra->current->spec.setCategory(true);
6673 BEGIN( ClassCategory );
6674 }
6675 else if (yyextra->insideCS && *yytext=='(') // C# 12 primary constructor
6676 {
6677 yyextra->current->args=yytext;
6678 yyextra->currentArgumentContext = ClassVar;
6679 yyextra->fullArgString = yyextra->current->args;
6680 yyextra->copyArgString = &yyextra->current->args;
6681 BEGIN( ReadFuncArgType ) ;
6682 }
6683 else
6684 {
6685 // probably a function anyway
6686 unput(*yytext);
6687 BEGIN( FindMembers );
6688 }
6689 }
6690<CSConstraintType,CSConstraintName>{CCS}{CCE} { /* empty comment */ }
6691<CSConstraintType,CSConstraintName>({CCS}[*!]|{CPPC}[/!])("<"?) { // special comment
6692 yyextra->fullArgString.clear();
6693 yyextra->lastCopyArgChar='#'; // end marker
6694 yyextra->lastCommentInArgContext=YY_START;
6695 if (yytext[1]=='/')
6696 BEGIN( CopyArgCommentLine );
6697 else
6698 BEGIN( CopyArgComment );
6699 }
6700<CSConstraintType,CSConstraintName>"#" { // artificially inserted token to signal end of comment block
6701 yyextra->current->typeConstr.back().docs = yyextra->fullArgString;
6702 }
6703<CSConstraintType>"=>" { // end of type constraint reached
6704 // parse documentation of the constraints
6705 handleParametersCommentBlocks(yyscanner,yyextra->current->typeConstr);
6706 unput('>');
6707 unput('=');
6708 BEGIN( yyextra->lastCSConstraint );
6709 }
6710<CSConstraintType>"{" { // end of type constraint reached
6711 // parse documentation of the constraints
6712 handleParametersCommentBlocks(yyscanner,yyextra->current->typeConstr);
6713 unput('{');
6714 BEGIN( yyextra->lastCSConstraint );
6715 }
6716<CSConstraintType,CSConstraintName>";" {
6717 handleParametersCommentBlocks(yyscanner,yyextra->current->typeConstr);
6718 unput(';');
6719 BEGIN( yyextra->lastCSConstraint );
6720 }
6721<CSConstraintName>":" {
6722 BEGIN( CSConstraintType );
6723 }
6724<CSConstraintName>{ID} {
6725 // parameter name
6726 yyextra->current->typeConstr.back().name=yytext;
6727 }
6728<CSConstraintType>"where" { // another constraint for a different param
6729 yyextra->current->typeConstr.push_back(Argument());
6730 BEGIN( CSConstraintName );
6731 }
6732<CSConstraintType>({ID}".")*{ID}("<"{ID}">")?("()")? {
6733 if (yyextra->current->typeConstr.back().type.empty())
6734 // first type constraint for this parameter
6735 {
6736 yyextra->current->typeConstr.back().type=yytext;
6737 }
6738 else // new type constraint for same parameter
6739 {
6740 DString name = yyextra->current->typeConstr.back().name;
6741 yyextra->current->typeConstr.push_back(Argument());
6742 yyextra->current->typeConstr.back().name=name;
6743 yyextra->current->typeConstr.back().type=yytext;
6744 }
6745 }
char & back()
Returns a reference to the last character.
Definition dstring.h:203
6746<CSConstraintName,CSConstraintType>\n {
6747 lineCount(yyscanner);
6748 }
6749<CSConstraintName,CSConstraintType>. {
6750 }
6751<ClassCategory>{ID} {
6752 yyextra->current->name+=yytext;
6753 }
6754<ClassCategory>")"/{BN}*"{" {
6755 yyextra->current->name+=')';
6756 BEGIN( ClassVar );
6757 }
6758<ClassCategory>")"/{BN}*"<" {
6759 yyextra->current->name+=')';
6760 BEGIN( ObjCProtocolList );
6761 }
6762<ClassCategory>")" {
6763 yyextra->current->name+=')';
6764 if (yyextra->current->spec.isProtocol() || yyextra->current->section.isObjcImpl())
6765 {
6766 unput('{'); // fake start of body
6767 }
6768 else // category has no variables so push back an empty body
6769 {
6770 unput('}');
6771 unput('{');
6772 }
6773 BEGIN( ClassVar );
6774 }
6775<ClassVar>":" {
6776 if (yyextra->current->section.isVariable()) // enum A B:2, see bug 748208
6777 {
6778 yyextra->current->bitfields+=":";
6779 yyextra->current->args.clear();
6780 BEGIN(BitFields);
6781 }
6782 else if (yyextra->current->section.isEnum()) // enum E:2, see bug 313527,
6783 // or C++11 style enum: 'E : unsigned int {...}'
6784 {
6785 yyextra->current->args.clear();
6786 BEGIN(EnumBaseType);
6787 }
6788 else
6789 {
6790 yyextra->current->type.clear();
6791 if (yyextra->current->spec.isInterface() ||
6792 yyextra->current->spec.isStruct() ||
6793 yyextra->current->spec.isRef() ||
6794 yyextra->current->spec.isValue() ||
6795 yyextra->insidePHP || yyextra->insideCS || yyextra->insideD || yyextra->insideObjC || yyextra->insideIDL
6796 )
6797 {
6798 yyextra->baseProt = Protection::Public;
6799 }
6800 else
6801 {
6802 yyextra->baseProt = Protection::Private;
6803 }
6804 yyextra->baseVirt = Specifier::Normal;
6805 yyextra->baseName.clear();
6806 BEGIN( BasesProt ) ;
6807 }
6808 }
6809<ClassVar>[;=*&] {
6810 if (yyextra->isTypedef) // typedef of a class, put typedef keyword back
6811 {
6812 yyextra->current->type.prepend("typedef");
6813 }
6814 if ((yytext[0]=='*' || yytext[0]=='&') && yyextra->current->section.isEnum())
6815 { // found "enum a *b" -> variable
6816 yyextra->current->section = EntryType::makeVariable() ;
6817 }
6818 if (yytext[0]==';' && yyextra->current->section.isEnum())
6819 {
6820 yyextra->current->reset();
6821 initEntry(yyscanner);
6822 }
6823 else
6824 {
6825 unput(*yytext);
6826 }
6827 BEGIN( FindMembers );
6828 }
6829<Bases,ClassVar>{CPPC}"/"/[^/] {
6830 if (!yyextra->insideObjC)
6831 {
6832 REJECT;
6833 }
6834 else
6835 {
6836 lineCount(yyscanner);
6837 yyextra->current->program << yytext;
6838 yyextra->current->fileName = yyextra->fileName ;
6839 yyextra->current->startLine = yyextra->yyLineNr ;
6840 yyextra->current->startColumn = yyextra->yyColNr;
6841 yyextra->curlyCount=0;
6842 BEGIN( ReadBodyIntf );
6843 }
6844 }
6845<Bases,ClassVar>({CPPC}{B}*)?{CCS}"*"/{NCOMM} |
6846<Bases,ClassVar>({CPPC}{B}*)?{CCS}"!" |
6847<Bases,ClassVar>{CPPC}"!" |
6848<Bases,ClassVar>[\-+]{BN}* {
6849 if (!yyextra->insideObjC)
6850 {
6851 REJECT;
6852 }
6853 else
6854 {
6855 lineCount(yyscanner);
6856 yyextra->current->program << yytext;
6857 yyextra->current->fileName = yyextra->fileName ;
6858 yyextra->current->startLine = yyextra->yyLineNr ;
6859 yyextra->current->startColumn = yyextra->yyColNr;
6860 yyextra->curlyCount=0;
6861 BEGIN( ReadBodyIntf );
6862 }
6863 }
6864<CompoundName,ClassVar>{B}*"{"{B}* {
6865 yyextra->current->program.str(std::string());
6866 yyextra->current->fileName = yyextra->fileName ;
6867 yyextra->current->bodyLine = yyextra->yyLineNr;
6868 yyextra->current->bodyColumn = yyextra->yyColNr;
6869 yyextra->current->name = removeRedundantWhiteSpace(yyextra->current->name);
6870 if (yyextra->current->name.empty() && !yyextra->isTypedef) // anonymous compound
6871 {
6872 if (yyextra->current->section.isNamespace()) // allow reopening of anonymous namespaces
6873 {
6874 if (Config_getBool(EXTRACT_ANON_NSPACES)) // use visible name
6875 {
6876 yyextra->current->name="anonymous_namespace{"+stripPath(yyextra->current->fileName)+"}";
6877 }
6878 else // use invisible name
6879 {
6880 yyextra->current->name = generateAnonymousAnchor(yyextra->fileName,yyextra->anonNSCount);
6881 }
6882 }
6883 else
6884 {
6885 yyextra->current->name = generateAnonymousAnchor(yyextra->fileName,yyextra->anonCount++);
6886 }
6887 }
6888 yyextra->curlyCount=0;
6889 if (yyextra->current_root && // not a nested struct yyextra->inside an @interface section
6890 !yyextra->current_root->spec.isInterface() &&
6891 (yyextra->current->spec.isInterface() ||
6892 yyextra->current->spec.isProtocol() ||
6893 yyextra->current->spec.isCategory() ||
6894 yyextra->current->section.isObjcImpl()
6895 ) &&
6896 yyextra->insideObjC
6897 )
6898 { // ObjC body that ends with @end
6899 BEGIN( ReadBodyIntf );
6900 }
6901 else if (yyextra->current->section.isNamespace())
6902 { // namespace body
6903 BEGIN( ReadNSBody );
6904 }
6905 else
6906 { // class body
6907 BEGIN( ReadBody ) ;
6908 }
6909 }
DString stripPath(const DString &s)
Definition util.cpp:3961
6910<BasesProt>"virtual"{BN}+ { lineCount(yyscanner); yyextra->baseVirt = Specifier::Virtual; }
6911<BasesProt>"public"{BN}+ { lineCount(yyscanner); yyextra->baseProt = Protection::Public; }
6912<BasesProt>"protected"{BN}+ { lineCount(yyscanner); yyextra->baseProt = Protection::Protected; }
6913<BasesProt>"internal"{BN}+ { if (!yyextra->insideCli) REJECT ; lineCount(yyscanner); yyextra->baseProt = Protection::Package; }
6914<BasesProt>"private"{BN}+ { lineCount(yyscanner); yyextra->baseProt = Protection::Private; }
6915<BasesProt>{BN} { lineCount(yyscanner); }
6916<BasesProt>. { unput(*yytext); BEGIN(Bases); }
6917<Bases>"decltype"{BN}*"(" {
6918 lineCount(yyscanner);
6919 yyextra->roundCount=0;
6920 yyextra->lastSkipRoundContext=YY_START;
6921 BEGIN(SkipRound);
6922 }
6923<Bases>("\\")?({ID}"\\")*{ID} { // PHP namespace token, not sure if interspacing is allowed but it gives problems (see bug 640847)
6924 if (!yyextra->insidePHP)
6925 {
6926 REJECT;
6927 }
6928 else // PHP base class of the form \Ns\Cl or Ns\Cl
6929 {
6930 lineCount(yyscanner);
6931 DString bn=yytext;
6932 bn = substitute(bn,"\\","::");
6933 yyextra->baseName += bn;
6934 yyextra->current->args += ' ';
6935 yyextra->current->args += yytext;
6936 }
6937 }
6938<Bases>("::")?{BN}*({ID}{BN}*"::"{BN}*)*{ID}("...")? {
6939 lineCount(yyscanner);
6940 DString baseScope = yytext;
6941 if (yyextra->insideCS && baseScope.stripWhiteSpace()=="where")
6942 {
6943 // type constraint for a class
6944 yyextra->current->typeConstr.clear();
6945 yyextra->current->typeConstr.push_back(Argument());
6946 yyextra->lastCSConstraint = YY_START;
6947 BEGIN( CSConstraintName );
6948 }
6949 else
6950 {
6951 yyextra->baseName+=yytext;
6952 yyextra->current->args += ' ';
6953 yyextra->current->args += yytext;
6954 }
6955 }
6956<Bases>{BN}*{ID}("."{ID})* { // Java style class
6957 DString name = substitute(yytext,".","::");
6958 yyextra->baseName += name;
6959 yyextra->current->args += ' ';
6960 yyextra->current->args += name;
6961 }
6962<ClassVar,Bases>\n/{BN}*[^{, \t\n:] {
6963 if (!yyextra->insideObjC)
6964 {
6965 REJECT;
6966 }
6967 else
6968 {
6969 lineCount(yyscanner);
6970 unput('{');
6971 }
6972 }
6973<ClassVar,Bases>"@end" { // empty ObjC interface
6974 unput('d'); // insert fake body: {}@end
6975 unput('n');
6976 unput('e');
6977 unput('@');
6978 unput('}');
6979 unput('{');
6980 }
6981<ClassVar>"<" { yyextra->current->name += *yytext;
6982 yyextra->sharpCount=1;
6983 yyextra->roundCount=0;
6984 yyextra->lastSkipSharpContext = YY_START;
6985 yyextra->specName = &yyextra->current->name;
6986 BEGIN ( Specialization );
6987 }
6988<Bases>{BN}*"<" {
6989 lineCount(yyscanner);
6990 yyextra->sharpCount=1;
6991 yyextra->roundCount=0;
6992 yyextra->lastSkipSharpContext = YY_START;
6993 if (yyextra->insideObjC) // start of protocol list
6994 {
6995 unput(',');
6996 }
6997 else // template specialization
6998 {
6999 //if (yyextra->insideCS) // generic
7000 //{
7001 // yyextra->baseName+="-g";
7002 //}
7003 yyextra->templateStr = yytext;
7004 yyextra->specName = &yyextra->templateStr;
7005 BEGIN ( Specialization );
7006 }
7007 }
7008<Specialization>"<" { *yyextra->specName += *yytext;
7009 if (yyextra->roundCount==0) yyextra->sharpCount++;
7010 }
7011<Specialization>">" {
7012 *yyextra->specName += *yytext;
7013 if (yyextra->roundCount==0 && --yyextra->sharpCount<=0)
7014 {
7015 yyextra->baseName+=removeRedundantWhiteSpace(*yyextra->specName);
7016 BEGIN(yyextra->lastSkipSharpContext);
7017 }
7018 }
7019<Specialization>{BN}+ { lineCount(yyscanner); *yyextra->specName +=' '; }
7020<Specialization>"<<" { *yyextra->specName += yytext; }
7021<Specialization>">>"/{B}*"::" { // M$ C++ extension to allow >> to close a template...
7022 unput('>');
7023 unput(' ');
7024 unput('>');
7025 }
7026<Specialization>">>" {
7027 if (yyextra->insideCS) // for C# >> ends a nested template
7028 {
7029 REJECT;
7030 }
7031 else // for C++ >> is a bitshift
7032 // operator and > > would end
7033 // a nested template.
7034 // We require the bitshift to be enclosed in braces.
7035 // See http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2005/n1757.html
7036 {
7037 if (yyextra->roundCount>0)
7038 {
7039 *yyextra->specName += yytext;
7040 }
7041 else
7042 {
7043 unput('>');
7044 unput(' ');
7045 unput('>');
7046 }
7047 }
7048 }
7049<Specialization>"typename"{BN}+ { lineCount(yyscanner); }
7050<Specialization>"(" { *yyextra->specName += *yytext; yyextra->roundCount++; }
7051<Specialization>")" { *yyextra->specName += *yytext; yyextra->roundCount--; }
7052
7053<Specialization>"\\\\" { *yyextra->specName += *yytext;}
7054<Specialization>"\\'" { *yyextra->specName += *yytext;}
7055<Specialization>"\\\"" { *yyextra->specName += *yytext;}
7056<Specialization>"'" { *yyextra->specName += *yytext;BEGIN(SpecializationSingleQuote);}
7057<Specialization>"\"" { *yyextra->specName += *yytext;BEGIN(SpecializationDoubleQuote);}
7058<SpecializationSingleQuote,SpecializationDoubleQuote>"\\\\" { *yyextra->specName += *yytext;}
7059<SpecializationSingleQuote>"\\'" { *yyextra->specName += *yytext;}
7060<SpecializationSingleQuote>"'" { *yyextra->specName += *yytext; BEGIN(Specialization);}
7061<SpecializationDoubleQuote>"\\\"" { *yyextra->specName += *yytext;}
7062<SpecializationDoubleQuote>"\"" { *yyextra->specName += *yytext; BEGIN(Specialization);}
7063<SpecializationSingleQuote,SpecializationDoubleQuote>. { *yyextra->specName += *yytext;}
7064
7065<Specialization>. {
7066 *yyextra->specName += *yytext;
7067 }
7068<SkipRound>"(" { ++yyextra->roundCount; }
7069<SkipRound>")" { if (--yyextra->roundCount<0)
7070 BEGIN ( yyextra->lastSkipRoundContext );
7071 }
7072<SkipRound>\" {
7073 yyextra->lastStringContext=SkipRound;
7074 BEGIN(SkipString);
7075 }
7076<Bases>","|(">"({BN}*"{")?)|({BN}+"implements"{BN}*) { lineCount(yyscanner);
7077 if (yyextra->insideProtocolList)
7078 {
7079 yyextra->baseName+="-p";
7080 }
7081 else
7082 {
7083 yyextra->current->args += ',' ;
7084 }
7085 yyextra->current->name = removeRedundantWhiteSpace(yyextra->current->name);
7086 if (!yyextra->baseName.empty())
7087 {
7088 yyextra->current->extends.emplace_back(
7089 yyextra->baseName,yyextra->baseProt,yyextra->baseVirt
7090 );
7091 }
7092 if (yyextra->current->spec.isInterface() || yyextra->current->spec.isStruct() ||
7093 yyextra->insideJava || yyextra->insidePHP || yyextra->insideCS ||
7094 yyextra->insideD || yyextra->insideObjC || yyextra->insideIDL || yyextra->insideSlice)
7095 {
7096 yyextra->baseProt=Protection::Public;
7097 }
7098 else
7099 {
7100 yyextra->baseProt=Protection::Private;
7101 }
7102 yyextra->baseVirt=Specifier::Normal;
7103 yyextra->baseName.clear();
7104 if (*yytext=='>')
7105 { // end of a ObjC protocol list
7106 yyextra->insideProtocolList=false;
7107 if (yyleng==1)
7108 {
7109 if (yyextra->insideObjC && !yyextra->current->spec.isProtocol())
7110 {
7111 BEGIN(ClassVar); // allow parsing of ':' for base class
7112 }
7113 else
7114 {
7115 unput('{'); // dummy start body
7116 }
7117 }
7118 else
7119 {
7120 yyless(1);
7121 }
7122 }
7123 else
7124 {
7125 if (*yytext==',' && yyextra->insideObjC) // Begin of protocol list
7126 {
7127 yyextra->insideProtocolList=true;
7128 }
7129 BEGIN(BasesProt);
7130 }
7131 }
7132<Bases>{B}*"{"{B}* {
7133 yyextra->current->program.str(std::string());
7134 yyextra->current->fileName = yyextra->fileName ;
7135 yyextra->current->bodyLine = yyextra->yyLineNr;
7136 yyextra->current->bodyColumn = yyextra->yyColNr;
7137 yyextra->current->name = removeRedundantWhiteSpace(yyextra->current->name);
7138 if (!yyextra->baseName.empty())
7139 {
7140 yyextra->current->extends.emplace_back(
7141 yyextra->baseName,yyextra->baseProt,yyextra->baseVirt
7142 );
7143 yyextra->baseName.clear();
7144 }
7145 yyextra->curlyCount=0;
7146 if (yyextra->insideObjC)
7147 {
7148 BEGIN( ReadBodyIntf );
7149 }
7150 else
7151 {
7152 BEGIN( ReadBody ) ;
7153 }
7154 }
7155<SkipUnionSwitch>{B}*"(" {
7156 yyextra->roundCount++;
7157 }
7158<SkipUnionSwitch>")" {
7159 if (--yyextra->roundCount==0)
7160 {
7161 BEGIN(ClassVar);
7162 }
7163 }
7164<SkipUnionSwitch>\n { lineCount(yyscanner); }
7165<SkipUnionSwitch>.
7166<Comment>{BN}+ { yyextra->current->program << yytext ;
7167 lineCount(yyscanner) ;
7168 }
7169<Comment>{CCS} { yyextra->current->program << yytext ; }
7170<Comment>{CPPC} { yyextra->current->program << yytext ; }
7171<Comment>{CMD}("code"|"verbatim"|"iliteral") {
7172 if (yyextra->doxygenComment) yyextra->insideCode=true;
7173 yyextra->current->program << yytext ;
7174 }
7175<Comment>{CMD}("endcode"|"endverbatim"|"endiliteral") {
7176 if (yyextra->doxygenComment) yyextra->insideCode=false;
7177 yyextra->current->program << yytext ;
7178 }
7179<Comment>[^ \.\t\r\n\/\*]+ { yyextra->current->program << yytext ; }
7180<Comment>{CCE} { yyextra->current->program << yytext ;
7181 if (!yyextra->insideCode)
7182 {
7183 yyextra->doxygenComment=false;
7184 BEGIN( yyextra->lastContext );
7185 }
7186 }
7187<Comment>. { yyextra->current->program << *yytext ; }
7188
7189<FindMembers,FindFields,MemberSpec,FuncQual,SkipCurly,Operator,ClassVar,SkipInits,SkipC11Inits,ReadExpressionBody,Bases,OldStyleArgs>({CPPC}{B}*)?{CCS}"!" {
7190 //printf("Start doc block at %d\n",yyextra->yyLineNr);
7191 if (!yyextra->current->doc.empty())
7192 {
7193 yyextra->current->doc+="\n\n";
7194 }
7195 else
7196 {
7197 yyextra->current->docLine = yyextra->yyLineNr;
7198 yyextra->current->docFile = yyextra->fileName;
7199 }
7200
7201 yyextra->lastDocContext = YY_START;
7202 if (yyextra->current_root->section.isScope())
7203 {
7204 yyextra->current->inside = yyextra->current_root->name+"::";
7205 }
7206 yyextra->docBlockContext = YY_START;
7207 yyextra->docBlockInBody = YY_START==SkipCurly || YY_START==ReadExpressionBody;
7208 yyextra->docBlockAutoBrief = Config_getBool(QT_AUTOBRIEF);
7209
7210 DString indent;
7211 indent.fill(' ',computeIndent(yytext,yyextra->column));
7212 yyextra->docBlock.str(indent.str());
7213
7214 if (yyextra->docBlockAutoBrief)
7215 {
7216 yyextra->current->briefLine = yyextra->yyLineNr;
7217 yyextra->current->briefFile = yyextra->fileName;
7218 }
7219 startCommentBlock(yyscanner,false);
7220 BEGIN( DocBlock );
7221 }
7222<FindMembers,FindFields,MemberSpec,FuncQual,SkipCurly,Operator,ClassVar,SkipInits,ReadExpressionBody,Bases,OldStyleArgs>{CCS}"*"[*]+{BL} {
7223 bool javadocBanner = Config_getBool(JAVADOC_BANNER);
7224 lineCount(yyscanner);
7225
7226 if( javadocBanner )
7227 {
7228 yyextra->lastDocContext = YY_START;
7229
7230 //printf("Found comment banner at %s:%d\n",yyextra->fileName,yyextra->yyLineNr);
7231 if (yyextra->current_root->section.isScope())
7232 {
7233 yyextra->current->inside = yyextra->current_root->name+"::";
7234 }
7235 yyextra->current->docLine = yyextra->yyLineNr;
7236 yyextra->current->docFile = yyextra->fileName;
7237 yyextra->docBlockContext = YY_START;
7238 yyextra->docBlockInBody = YY_START==SkipCurly || YY_START==ReadExpressionBody;
7239 bool javadocAutoBrief = Config_getBool(JAVADOC_AUTOBRIEF);
7240 yyextra->docBlockAutoBrief = javadocAutoBrief;
7241
7242 DString indent;
7243 indent.fill(' ',computeIndent(yytext,yyextra->column));
7244 yyextra->docBlock.str(indent.str());
7245
7246 if (yyextra->docBlockAutoBrief)
7247 {
7248 yyextra->current->briefLine = yyextra->yyLineNr;
7249 yyextra->current->briefFile = yyextra->fileName;
7250 }
7251 startCommentBlock(yyscanner,false);
7252 BEGIN( DocBlock );
7253 }
7254 else
7255 {
7256 yyextra->current->program << yytext ;
7257 yyextra->lastContext = YY_START ;
7258 yyextra->doxygenComment=true;
7259 BEGIN( Comment ) ;
7260 }
7261 }
7262<FindMembers,FindFields,MemberSpec,FuncQual,SkipCurly,Operator,ClassVar,ReadExpressionBody,SkipInits,Bases,OldStyleArgs>^{B}+({CPPC}{B}*)?{CCS}"*"/{NCOMM} {
7263 lineCount(yyscanner);
7264 yyextra->yyColNr=1;
7265 REJECT;
7266 }
7267<FindMembers,FindFields,MemberSpec,FuncQual,SkipCurly,ReadExpressionBody,Operator,ClassVar,SkipInits,Bases,OldStyleArgs>({CPPC}{B}*)?{CCS}"*"/{NCOMM} {
7268 yyextra->lastDocContext = YY_START;
7269
7270 //printf("Found comment block at %s:%d\n",yyextra->fileName,yyextra->yyLineNr);
7271 if (yyextra->current_root->section.isScope())
7272 {
7273 yyextra->current->inside = yyextra->current_root->name+"::";
7274 }
7275 yyextra->current->docLine = yyextra->yyLineNr;
7276 yyextra->current->docFile = yyextra->fileName;
7277 yyextra->docBlockContext = YY_START;
7278 yyextra->docBlockInBody = YY_START==SkipCurly || YY_START==ReadExpressionBody;
7279 bool javadocAutoBrief = Config_getBool(JAVADOC_AUTOBRIEF);
7280 yyextra->docBlockAutoBrief = javadocAutoBrief;
7281
7282 DString indent;
7283 indent.fill(' ',computeIndent(yytext,yyextra->column));
7284 yyextra->docBlock.str(indent.str());
7285
7286 if (yyextra->docBlockAutoBrief)
7287 {
7288 yyextra->current->briefLine = yyextra->yyLineNr;
7289 yyextra->current->briefFile = yyextra->fileName;
7290 }
7291 startCommentBlock(yyscanner,false);
7292 BEGIN( DocBlock );
7293 }
7294<FindMembers,FindFields,MemberSpec,SkipCurly,ReadExpressionBody,FuncQual,Operator,ClassVar,Bases,OldStyleArgs>{CPPC}"!" {
7295 yyextra->lastDocContext = YY_START;
7296 if (yyextra->current_root->section.isScope())
7297 {
7298 yyextra->current->inside = yyextra->current_root->name+"::";
7299 }
7300 yyextra->docBlockContext = YY_START;
7301 yyextra->docBlockInBody = YY_START==SkipCurly || YY_START==ReadExpressionBody;
7302 yyextra->docBlockAutoBrief = false;
7303
7304 DString indent;
7305 indent.fill(' ',computeIndent(yytext,yyextra->column));
7306 yyextra->docBlock.str(indent.str());
7307
7308 startCommentBlock(yyscanner,yyextra->current->brief.empty());
7309 BEGIN( DocLine );
7310 }
7311<FindMembers,FindFields,MemberSpec,SkipCurly,ReadExpressionBody,FuncQual,Operator,ClassVar,Bases,OldStyleArgs>{CPPC}"/"/[^/] {
7312 yyextra->lastDocContext = YY_START;
7313 if (yyextra->current_root->section.isScope())
7314 {
7315 yyextra->current->inside = yyextra->current_root->name+"::";
7316 }
7317 yyextra->docBlockContext = YY_START;
7318 yyextra->docBlockInBody = YY_START==SkipCurly || YY_START==ReadExpressionBody;
7319 yyextra->docBlockAutoBrief = false;
7320 DString indent;
7321 indent.fill(' ',computeIndent(yytext,yyextra->column));
7322 yyextra->docBlock.str(indent.str());
7323 startCommentBlock(yyscanner,yyextra->current->brief.empty());
7324 BEGIN( DocLine );
7325 }
7326<FindMembers>"extern"{BN}*"\""[^\"]+"\""{BN}*("{")? {
7327 lineCount(yyscanner);
7328 yyextra->externLinkage=true;
7329 }
7330<FindMembers>"{" {
7331 if (yyextra->externLinkage)
7332 {
7333 yyextra->externLinkage=false;
7334 }
7335 else if (yyextra->insideCS &&
7336 !yyextra->current->name.empty() &&
7337 !yyextra->current->type.empty())
7338 {
7339 if (yyextra->current->mtype == MethodTypes::Event)
7340 {
7341 yyextra->mtype = MethodTypes::Event;
7342 }
7343 else if (yyextra->current->type.containsWord("event")) // event
7344 {
7345 yyextra->current->mtype = yyextra->mtype = MethodTypes::Event;
7346 }
7347 else // property
7348 {
7349 yyextra->current->mtype = yyextra->mtype = MethodTypes::Property;
7350 }
7351 yyextra->current->bodyLine = yyextra->yyLineNr;
7352 yyextra->current->bodyColumn = yyextra->yyColNr;
7353 yyextra->curlyCount=0;
7354 BEGIN( CSAccessorDecl );
7355 }
7356 else if (yyextra->insideIDL && yyextra->current->spec.isAttribute())
7357 {
7358 // UNO IDL: attributes may have setter and getter
7359 // exception specifications
7360 yyextra->current->exception = " {";
7361 BEGIN(UNOIDLAttributeBlock);
7362 }
7363 else
7364 {
7365 if ((yyextra->insideJava || yyextra->insideCS || yyextra->insideD) &&
7366 yyextra->current->name.empty()
7367 )
7368 {
7369 // static Java initializer
7370 yyextra->needsSemi = false;
7371 if (yyextra->current->isStatic)
7372 {
7373 yyextra->current->name="[static initializer]";
7374 yyextra->current->type.clear();
7375 }
7376 else
7377 {
7378 yyextra->current->name="[instance initializer]";
7379 }
7380 unput(*yytext);
7381 BEGIN( SFunction );
7382 }
7383 else
7384 {
7385 // pre C++11 code -> ignore the initializer
7386 //yyextra->needsSemi = true;
7387 //yyextra->current->type.clear();
7388 //yyextra->current->name.clear();
7389 //yyextra->current->args.clear();
7390 //yyextra->current->argList.clear();
7391 //yyextra->curlyCount=0;
7392 //BEGIN( SkipCurlyBlock );
7393
7394 // C++11 style initializer list
7395 yyextra->current->bodyLine = yyextra->yyLineNr;
7396 yyextra->current->bodyColumn = yyextra->yyColNr;
7397 yyextra->current->initializer.str(yytext);
7398 yyextra->lastInitializerContext = YY_START;
7399 yyextra->sharpCount=0;
7400 yyextra->initBracketCount=1;
7401 BEGIN(ReadInitializer);
7402 }
7403 }
7404 }
7405<CSAccessorDecl>"{" { yyextra->curlyCount++; }
7406<CSAccessorDecl>"}"{B}*"=" {
7407 // fall back to next rule if it's not the right bracket
7408 if (yyextra->curlyCount != 0) REJECT;
7409 yyextra->current->initializer.str("=");
7410 yyextra->current->endBodyLine=yyextra->yyLineNr;
7411 yyextra->lastInitializerContext = FindMembers;
7412 BEGIN(ReadInitializer);
7413 }
7414<CSAccessorDecl>"}" {
7415 if (yyextra->curlyCount)
7416 {
7417 yyextra->curlyCount--;
7418 }
7419 else
7420 {
7421 yyextra->mtype = MethodTypes::Method;
7422 yyextra->virt = Specifier::Normal;
7423 // not really important, but while we are at it
7424 yyextra->current->endBodyLine=yyextra->yyLineNr;
7425 unput(';');
7426 BEGIN(FindMembers);
7427 }
7428 }
7429<CSAccessorDecl>"private "{BN}*"set" { if (yyextra->curlyCount==0) yyextra->current->spec.setPrivateSettable(true); }
7430<CSAccessorDecl>"protected "{BN}*"set" { if (yyextra->curlyCount==0) yyextra->current->spec.setProtectedSettable(true); }
7431<CSAccessorDecl>"private "{BN}*"get" { if (yyextra->curlyCount==0) yyextra->current->spec.setPrivateGettable(true); }
7432<CSAccessorDecl>"protected "{BN}*"get" { if (yyextra->curlyCount==0) yyextra->current->spec.setProtectedGettable(true); }
7433<CSAccessorDecl>"set" { if (yyextra->curlyCount==0) yyextra->current->spec.setSettable(true); }
7434<CSAccessorDecl>"get" { if (yyextra->curlyCount==0) yyextra->current->spec.setGettable(true); }
7435<CSAccessorDecl>"add" { if (yyextra->curlyCount==0) yyextra->current->spec.setAddable(true); }
7436<CSAccessorDecl>"remove" { if (yyextra->curlyCount==0) yyextra->current->spec.setRemovable(true); }
7437<CSAccessorDecl>"raise" { if (yyextra->curlyCount==0) yyextra->current->spec.setRaisable(true); }
7438<CSAccessorDecl>{CHARLIT} {}
7439<CSAccessorDecl>"\"" { BEGIN(CSString);}
7440<CSAccessorDecl>"." {}
7441<CSAccessorDecl>\n { lineCount(yyscanner); }
7442<CSString>"\"" { BEGIN(CSAccessorDecl);}
7443<CSString>{CPPC} {} // Otherwise the rule <*>"//" will kick in
7444<CSString>{CCS} {} // Otherwise the rule <*>"/*" will kick in
7445<CSString>\n { lineCount(yyscanner); }
7446<CSString>"." {}
7447
7448 /* ---- Slice-specific rules ------ */
7449
7450<SliceSequence>{SCOPENAME} {
7451 if (yyextra->current->spec.isLocal())
7452 {
7453 yyextra->current->type = "local ";
7454 }
7455 yyextra->current->type += "sequence<";
7456 yyextra->current->type += yytext;
7457 yyextra->current->type += ">";
7458 }
7459
7460<SliceSequence>{BN}*">"{BN}* {
7461 lineCount(yyscanner);
7462 BEGIN(SliceSequenceName);
7463 }
7464
7465<SliceSequenceName>{ID}{BN}* {
7466 lineCount(yyscanner);
7467 yyextra->current->name = yytext ;
7468 yyextra->current->name = yyextra->current->name.stripWhiteSpace();
7469 }
7470
7471<SliceSequenceName>";" {
7472 yyextra->current->section = EntryType::makeVariable();
7473 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
7474 initEntry(yyscanner);
7475 BEGIN(FindMembers);
7476 }
7477
7478<SliceDictionary>{SCOPENAME}{BN}*","{BN}*{SCOPENAME} {
7479 lineCount(yyscanner);
7480 if (yyextra->current->spec.isLocal())
7481 {
7482 yyextra->current->type = "local ";
7483 }
7484 yyextra->current->type += "dictionary<";
7485 yyextra->current->type += yytext;
7486 yyextra->current->type += ">";
7487 yyextra->current->type = yyextra->current->type.simplifyWhiteSpace();
7488 }
7489
7490<SliceDictionary>{BN}*">"{BN}* {
7491 lineCount(yyscanner);
7492 BEGIN(SliceDictionaryName);
7493 }
7494
7495<SliceDictionaryName>{ID}{BN}* {
7496 lineCount(yyscanner);
7497 yyextra->current->name = yytext ;
7498 yyextra->current->name = yyextra->current->name.stripWhiteSpace();
7499 }
7500
7501<SliceDictionaryName>";" {
7502 yyextra->current->section = EntryType::makeVariable();
7503 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
7504 initEntry(yyscanner);
7505 BEGIN(FindMembers);
7506 }
7507
7508 /**********************************************************************************/
7509 /******************** Documentation block related rules ***************************/
7510 /**********************************************************************************/
7511
7512 /* ---- Single line comments ------ */
7513<DocLine>[^\n]*"\n"[ \t]*{CPPC}[/!][<]? { // continuation of multiline C++-style comment
7514 int markerLen = yytext[yyleng-1]=='<' ? 4 : 3;
7515 yyextra->docBlock << std::string(yytext).substr(0,yyleng-markerLen);
7516 lineCount(yyscanner);
7517 }
7518<DocLine>{B}*{CPPC}"/"[/]+{Bopt}/"\n" { // ignore marker line (see bug700345)
7519 handleCommentBlock(yyscanner,yyextra->docBlock.str(),yyextra->current->brief.empty());
7520 BEGIN( yyextra->docBlockContext );
7521 }
7522<DocLine>{NONLopt}/"\n"{B}*{CPPC}[!/]{B}*{CMD}"}" { // next line is an end group marker, see bug 752712
7523 yyextra->docBlock << yytext;
7524 handleCommentBlock(yyscanner,yyextra->docBlock.str(),yyextra->current->brief.empty());
7525 BEGIN( yyextra->docBlockContext );
7526 }
7527<DocLine>{NONLopt}/"\n" { // whole line
7528 yyextra->docBlock << yytext;
7529 handleCommentBlock(yyscanner,yyextra->docBlock.str(),yyextra->current->brief.empty());
7530 BEGIN( yyextra->docBlockContext );
7531 }
7532
7533 /* ---- Comments blocks ------ */
7534
7535<DocBlock>"*"*{CCE} { // end of comment block
7536 handleCommentBlock(yyscanner,yyextra->docBlock.str(),false);
7537 BEGIN(yyextra->docBlockContext);
7538 }
7539<DocBlock>"\\ilinebr "{B}*"*"/[^/] {
7540 DString indent;
7541 indent.fill(' ',computeIndent(yytext+8,yyextra->column));
7542 yyextra->docBlock << "\\ilinebr " << indent;
7543 }
7544<DocBlock>^{B}*"*"+/[^/] {
7545 DString indent;
7546 indent.fill(' ',computeIndent(yytext,yyextra->column));
7547 yyextra->docBlock << indent;
7548 }
7549<DocBlock>^{B}*({CPPC})?{B}*"*"+/[^/a-z_A-Z0-9*] { // start of a comment line
7550 DString indent;
7551 indent.fill(' ',computeIndent(yytext,yyextra->column));
7552 yyextra->docBlock << indent;
7553 }
7554<DocBlock>^{B}*({CPPC}){B}* { // strip embedded C++ comments if at the start of a line
7555 }
7556<DocBlock>{CPPC} { // slashes in the middle of a comment block
7557 yyextra->docBlock << yytext;
7558 }
7559<DocBlock>{CCS} { // start of a new comment in the
7560 // middle of a comment block
7561 yyextra->docBlock << yytext;
7562 }
7563<DocBlock>({CMD}{CMD}){ID}/[^a-z_A-Z0-9] { // escaped command
7564 yyextra->docBlock << yytext;
7565 }
7566<DocBlock>{CMD}("f$"|"f["|"f{"|"f(") {
7567 yyextra->docBlock << yytext;
7568 char blockName[] = "f$";
7569 char c = yytext[2];
7570 if (c=='[') blockName[1]=']';
7571 else if (c=='{') blockName[1]='}';
7572 else if (c=='(') blockName[1]=')';
7573 startVerbatimBlock(yyscanner,blockName);
7574 BEGIN(DocCopyBlock);
7575 }
7576<DocBlock>{CMD}"ifile"{B}+"\""[^\n\"]+"\"" {
7577 yyextra->fileName = &yytext[6];
7578 yyextra->fileName = yyextra->fileName.stripWhiteSpace();
7579 yyextra->fileName = yyextra->fileName.mid(1,yyextra->fileName.length()-2);
7580 yyextra->docBlock << yytext;
7581 }
7582<DocBlock>{CMD}"ifile"{B}+{FILEMASK} {
7583 yyextra->fileName = &yytext[6];
7584 yyextra->fileName = yyextra->fileName.stripWhiteSpace();
7585 yyextra->docBlock << yytext;
7586 }
7587<DocBlock>{CMD}"iline"{LINENR}{B} {
7588 bool ok = false;
7589 int nr = DString(&yytext[6]).toInt(&ok);
7590 if (!ok)
7591 {
7592 warn(yyextra->fileName,yyextra->yyLineNr,"Invalid line number '{}' for iline command",yytext);
7593 }
7594 else
7595 {
7596 yyextra->yyLineNr = nr;
7597 }
7598 yyextra->docBlock << yytext;
7599 }
7600<DocBlock>{B}*"<"{PRE}">" {
7601 yyextra->docBlock << yytext;
7602 startVerbatimBlock(yyscanner,"<pre>");
7603 BEGIN(DocCopyBlock);
7604 }
7605<DocBlock>{CMD}"startuml"/[^a-z_A-Z0-9\-] { // verbatim command (which could contain nested comments!)
7606 yyextra->docBlock << yytext;
7607 startVerbatimBlock(yyscanner,"uml");
7608 BEGIN(DocCopyBlock);
7609 }
7610<DocBlock>{CMD}("verbatim"|"iliteral"|"latexonly"|"htmlonly"|"xmlonly"|"manonly"|"rtfonly"|"docbookonly"|"dot"|"msc"|"mermaid")/[^a-z_A-Z0-9\-] { // verbatim command (which could contain nested comments!)
7611 yyextra->docBlock << yytext;
7612 startVerbatimBlock(yyscanner,&yytext[1]);
7613 BEGIN(DocCopyBlock);
7614 }
7615<DocBlock>{CMD}("code")/[^a-z_A-Z0-9\-] { // verbatim command (which could contain nested comments!)
7616 yyextra->docBlock << yytext;
7617 startVerbatimBlock(yyscanner,&yytext[1],0,true);
7618 BEGIN(DocCopyBlock);
7619 }
7620<DocBlock>"\\ilinebr "({B}*"*"+)?{B}{0,3}"~~~"[~]* {
7621 DString pat = substitute(yytext+9,"*"," "); // skip over "\ilinebr " part
7622 yyextra->docBlock << "\\ilinebr ";
7623 yyextra->docBlock << pat;
7624 startVerbatimBlock(yyscanner,"~~~",pat.stripWhiteSpace().length(),true);
7625 BEGIN(DocCopyBlock);
7626 }
7627<DocBlock>^({B}*"*"+)?{B}{0,3}"~~~"[~]* {
7628 DString pat = substitute(yytext,"*"," ");
7629 yyextra->docBlock << pat;
7630 startVerbatimBlock(yyscanner,"~~~",pat.stripWhiteSpace().length(),true);
7631 BEGIN(DocCopyBlock);
7632 }
7633<DocBlock>"\\ilinebr "({B}*"*"+)?{B}{0,3}"```"[`]*/(".")?[a-zA-Z0-9#_-]+ |
7634<DocBlock>"\\ilinebr "({B}*"*"+)?{B}{0,3}"```"[`]*/"{"[^}]+"}" |
7635<DocBlock>"\\ilinebr "({B}*"*"+)?{B}{0,3}"```"[`]* {
7636 DString pat = substitute(yytext+9,"*"," "); // skip over "\ilinebr " part
7637 yyextra->docBlock << "\\ilinebr ";
7638 yyextra->docBlock << pat;
7639 startVerbatimBlock(yyscanner,"```",pat.stripWhiteSpace().length(),true);
7640 BEGIN(DocCopyBlock);
7641 }
7642<DocBlock>^({B}*"*"+)?{B}{0,3}"```"[`]*/(".")?[a-zA-Z0-9#_-]+ |
7643<DocBlock>^({B}*"*"+)?{B}{0,3}"```"[`]*/"{"[^}]+"}" |
7644<DocBlock>^({B}*"*"+)?{B}{0,3}"```"[`]* {
7645 DString pat = substitute(yytext,"*"," ");
7646 yyextra->docBlock << pat;
7647 startVerbatimBlock(yyscanner,"```",pat.stripWhiteSpace().length(),true);
7648 BEGIN(DocCopyBlock);
7649 }
7650<DocBlock>"```" { // skip ``` if not at the start of a line
7651 yyextra->docBlock << "```";
7652 }
7653<DocBlock>"\\`" { // skip escaped backtick
7654 yyextra->docBlock << yytext;
7655 }
7656<DocBlock>"`"{1,2} {
7657 yyextra->docBlock << yytext;
7658 startVerbatimBlock(yyscanner,yytext,yyleng,true);
7659 BEGIN(DocCopyBlock);
7660 }
7661<DocBlock>{B}*"<"{CODE}">" {
7662 if (yyextra->insideCS)
7663 {
7664 yyextra->docBlock << yytext;
7665 startVerbatimBlock(yyscanner,"<code>",0,true);
7666 BEGIN(DocCopyBlock);
7667 }
7668 else
7669 {
7670 REJECT;
7671 }
7672 }
7673<DocBlock>[^@*~`'\/\\\n]+ { // any character that isn't special
7674 yyextra->docBlock << yytext;
7675 }
7676<DocBlock>\n { // newline
7677 lineCount(yyscanner);
7678 yyextra->docBlock << *yytext;
7679 }
7680<DocBlock>. { // command block
7681 yyextra->docBlock << *yytext;
7682 }
7683
7684 /* ---- Copy verbatim sections ------ */
7685
7686<DocCopyBlock>"</"{PRE}">" { // end of a <pre> block
7687 if (endVerbatimBlock(yyscanner,"<pre>"))
7688 {
7689 BEGIN(DocBlock);
7690 }
7691 yyextra->docBlock << yytext;
7692 }
7693<DocCopyBlock>"</"{CODE}">" { // end of a <code> block
7694 if (endVerbatimBlock(yyscanner,"<code>"))
7695 {
7696 BEGIN(DocBlock);
7697 }
7698 yyextra->docBlock << yytext;
7699 }
7700<DocCopyBlock>[\\@]("f$"|"f]"|"f}"|"f)") {
7701 if (endVerbatimBlock(yyscanner,&yytext[1]))
7702 {
7703 BEGIN(DocBlock);
7704 }
7705 yyextra->docBlock << yytext;
7706 }
7707<DocCopyBlock>[\\@]("endverbatim"|"endiliteral"|"endlatexonly"|"endhtmlonly"|"endxmlonly"|"enddocbookonly"|"endmanonly"|"endrtfonly"|"enddot"|"endmsc"|"endmermaid"|"enduml"|"endcode")/[^a-z_A-Z0-9] { // end of verbatim block
7708 if (endVerbatimBlock(yyscanner,&yytext[4]))
7709 {
7710 BEGIN(DocBlock);
7711 }
7712 yyextra->docBlock << yytext;
7713 }
7714<DocCopyBlock>^{B}*"*"+/{BN}+ { // start of a comment line
7715 if ((yyextra->docBlockName=="verbatim") || (yyextra->docBlockName=="code") || (yyextra->docBlockName=="iliteral"))
7716 {
7717 REJECT;
7718 }
7719 else
7720 {
7721 DString indent;
7722 indent.fill(' ',computeIndent(yytext,0));
7723 yyextra->docBlock << indent;
7724 }
7725 }
7726<DocCopyBlock>^{B}*"*"+/{B}+"*"{BN}* { // start of a comment line with two *'s
7727 if ((yyextra->docBlockName=="code") || (yyextra->docBlockName=="iliteral"))
7728 {
7729 DString indent;
7730 indent.fill(' ',computeIndent(yytext,0));
7731 yyextra->docBlock << indent;
7732 }
7733 else
7734 {
7735 REJECT;
7736 }
7737 }
7738<DocCopyBlock>^{B}*"*"+/({ID}|"(") { // Assume *var or *(... is part of source code (see bug723516)
7739 if ((yyextra->docBlockName=="code") || (yyextra->docBlockName=="iliteral"))
7740 {
7741 DString indent;
7742 indent.fill(' ',computeIndent(yytext,-1));
7743 yyextra->docBlock << indent+"*";
7744 }
7745 else
7746 {
7747 REJECT;
7748 }
7749 }
7750<DocCopyBlock>^{B}*"*"+/{BN}* { // start of a comment line with one *
7751 if ((yyextra->docBlockName=="code") || (yyextra->docBlockName=="iliteral"))
7752 {
7753 DString indent;
7754 if (yyextra->nestedComment>0) // keep * it is part of the code
7755 {
7756 indent.fill(' ',computeIndent(yytext,-1));
7757 yyextra->docBlock << indent+"*";
7758 }
7759 else // remove * it is part of the comment block
7760 {
7761 indent.fill(' ',computeIndent(yytext,0));
7762 yyextra->docBlock << indent;
7763 }
7764 }
7765 else
7766 {
7767 REJECT;
7768 }
7769 }
7770<DocCopyBlock>^({B}*"*"+)?{B}{0,3}"~~~"[~]* {
7771 DString pat = substitute(yytext,"*"," ");
7772 if (endVerbatimBlock(yyscanner,"~~~",pat.stripWhiteSpace().length()))
7773 {
7774 BEGIN(DocBlock);
7775 }
7776 yyextra->docBlock << pat;
7777 }
7778<DocCopyBlock>^({B}*"*"+)?{B}{0,3}"```"[`]* {
7779 DString pat = substitute(yytext,"*"," ");
7780 if (endVerbatimBlock(yyscanner,"```",pat.stripWhiteSpace().length()))
7781 {
7782 BEGIN(DocBlock);
7783 }
7784 yyextra->docBlock << pat;
7785 }
7786<DocCopyBlock>"```" { // backtick + end marker
7787 if (yyextra->docBlockName=="``")
7788 {
7789 yyextra->docBlock << "`";
7790 endVerbatimBlock(yyscanner,"``",2);
7791 yyextra->docBlock << "``";
7792 BEGIN(DocBlock);
7793 }
7794 else
7795 {
7796 yyextra->docBlock << yytext;
7797 }
7798 }
7799<DocCopyBlock>"''"/[^a-z_A-Z0-9-] {
7800 if (!Config_getBool(MARKDOWN_STRICT) && endVerbatimBlock(yyscanner,"``",2))
7801 {
7802 BEGIN(DocBlock);
7803 }
7804 yyextra->docBlock << yytext;
7805 }
7806<DocCopyBlock>"'"/[^'a-z_A-Z0-9-] {
7807 if (!Config_getBool(MARKDOWN_STRICT) && endVerbatimBlock(yyscanner,"`",1))
7808 {
7809 BEGIN(DocBlock);
7810 }
7811 yyextra->docBlock << yytext;
7812 }
7813<DocCopyBlock>"`"{1,2} {
7814 if (endVerbatimBlock(yyscanner,yytext,yyleng))
7815 {
7816 BEGIN(DocBlock);
7817 }
7818 yyextra->docBlock << yytext;
7819 }
7820<DocCopyBlock>[^<@/\*\‍]`'~"\$\\\n]+ { // any character that is not special
7821 yyextra->docBlock << yytext;
7822 }
7823<DocCopyBlock>\" {
7824 yyextra->docBlock << yytext;
7825 if (yyextra->docBlockName=="code" || yyextra->docBlockName=="iliteral")
7826 // to support end of comment character sequences inside
7827 // a string literal of a code block, see #6737
7828 {
7829 yyextra->lastStringContext=YY_START;
7830 yyextra->pCopyQuotedGString=&yyextra->docBlock;
7831 yyextra->stopAtInvalidString=true;
7832 BEGIN(CopyGString);
7833 }
7834 }
7835<DocCopyBlock>{CCS}|{CCE}|{CPPC} {
7836 if (yytext[1]=='*') // start comment
7837 {
7838 yyextra->nestedComment++;
7839 }
7840 else if (yytext[0]=='*' && yyextra->nestedComment>0) // end comment
7841 {
7842 yyextra->nestedComment--;
7843 }
7844 else if (yytext[0]=='*' && yyextra->nestedComment==0 && yyextra->isCodeBlock) // end comment without start
7845 {
7846 warn(yyextra->fileName,yyextra->yyLineNr,
7847 "Found end of C comment inside a '{}' block without matching start of the comment!"
7848 " Maybe the end marker for the block is missing?",
7849 yyextra->docBlockName);
7850 BEGIN(DocBlock);
7851 }
7852 yyextra->docBlock << yytext;
7853 }
7854<DocCopyBlock>\n { // newline
7855 yyextra->docBlock << *yytext;
7856 lineCount(yyscanner);
7857 }
7858<DocCopyBlock>. { // any other character
7859 yyextra->docBlock << *yytext;
7860 }
7861<DocCopyBlock><<EOF>> {
7862 warn(yyextra->fileName,yyextra->yyLineNr,
7863 "reached end of file while inside a '{}' block!"
7864 " The command that should end the block seems to be missing!",
7865 yyextra->docBlockName);
7866 yyterminate();
7867 }
7868
7869
7870 /* ------------- Prototype parser -------------- */
7871
7872<Prototype>"operator"{B}*"("{B}*")" {
7873 yyextra->current->name+=yytext;
7874 }
7875<Prototype>"(" {
7876 yyextra->current->args+=*yytext;
7877 yyextra->currentArgumentContext = PrototypeQual;
7878 yyextra->fullArgString = yyextra->current->args;
7879 yyextra->copyArgString = &yyextra->current->args;
7880 BEGIN( ReadFuncArgType ) ;
7881 }
7882<Prototype>"("({ID}"::")*({B}*[&*])+ {
7883 if (yyextra->insidePHP) // reference parameter
7884 {
7885 REJECT;
7886 }
7887 else
7888 {
7889 yyextra->current->type+=yyextra->current->name+yytext;
7890 yyextra->current->name.clear();
7891 BEGIN( PrototypePtr );
7892 }
7893 }
7894<PrototypePtr>{SCOPENAME} {
7895 yyextra->current->name+=yytext;
7896 }
7897<PrototypePtr>"(" {
7898 yyextra->current->args+=*yytext;
7899 yyextra->currentArgumentContext = PrototypeQual;
7900 yyextra->fullArgString = yyextra->current->args;
7901 yyextra->copyArgString = &yyextra->current->args;
7902 BEGIN( ReadFuncArgType ) ;
7903 }
7904<PrototypePtr>")" {
7905 yyextra->current->type+=')';
7906 BEGIN( Prototype );
7907 }
7908<PrototypePtr>. {
7909 yyextra->current->name+=yytext;
7910 }
7911<PrototypeQual>"{" {
7912 BEGIN( PrototypeSkipLine);
7913 }
7914<PrototypeQual>{B}*"const"{B}* {
7915 yyextra->current->args += " const ";
7916 yyextra->current->argList.setConstSpecifier(true);
7917 }
7918<PrototypeQual>{B}*"volatile"{B}* {
7919 yyextra->current->args += " volatile ";
7920 yyextra->current->argList.setVolatileSpecifier(true);
7921 }
7922<PrototypeQual>{B}*"="{B}*"0"{B}* {
7923 yyextra->current->args += " = 0";
7924 yyextra->current->virt = Specifier::Pure;
7925 yyextra->current->argList.setPureSpecifier(true);
7926 }
7927<PrototypeQual>"throw"{B}*"(" {
7928 yyextra->current->exception = "throw(";
7929 BEGIN(PrototypeExc);
7930 }
7931<PrototypeExc>")" {
7932 yyextra->current->exception += ')';
7933 BEGIN(PrototypeQual);
7934 }
7935<PrototypeExc>. {
7936 yyextra->current->exception += *yytext;
7937 }
7938<PrototypeQual>. {
7939 yyextra->current->args += *yytext;
7940 }
7941<Prototype>. {
7942 yyextra->current->name += *yytext;
7943 }
7944<PrototypeSkipLine>. {
7945 }
7946
7947
7948
7949
7950<SkipCxxComment>.*"\\\n" { // line continuation
7951 if (yyextra->insideCS)
7952 {
7953 REJECT;
7954 }
7955 else
7956 {
7957 lineCount(yyscanner);
7958 }
7959 }
7960<SkipCxxComment>{ANYopt}/\n {
7961 BEGIN( yyextra->lastCContext ) ;
7962 }
7963<SkipComment>[^\*\n]+
7964
7965 /* ------------ Generic rules -------------- */
7966
7967<*>"[[" { // C++11 attribute
7968 if (!yyextra->insideCpp) REJECT;
7969 if (YY_START == CopyGString || YY_START == CopyGString) REJECT;
7970 yyextra->lastC11AttributeContext = YY_START;
7971 yyextra->pCopyC11AttributeString = &yyextra->current->attributes;
7972 BEGIN( CopyC11Attribute );
7973 }
7974
7975<*>\n { lineCount(yyscanner); }
7976<*>\" {
7977 if (yyextra->insideIDL && yyextra->insideCppQuote)
7978 {
7979 BEGIN(EndCppQuote);
7980 }
7981 else if (yyextra->insidePHP)
7982 {
7983 yyextra->lastStringContext=YY_START;
7984 BEGIN(SkipString);
7985 }
7986 }
7987<*>^{B}*"#" {
7988 if (!yyextra->insidePHP)
7989 {
7990 yyextra->lastCPPContext = YY_START;
7991 BEGIN( SkipCPP ) ;
7992 }
7993 else
7994 {
7995 yyextra->lastCContext = YY_START ;
7996 BEGIN( SkipCxxComment ) ;
7997 }
7998 }
7999<*>"#" {
8000 if (!yyextra->insidePHP)
8001 REJECT;
8002 yyextra->lastCContext = YY_START ;
8003 BEGIN( SkipCxxComment ) ;
8004 }
8005<*>\' {
8006 if (yyextra->insidePHP)
8007 {
8008 yyextra->lastStringContext=YY_START;
8009 BEGIN(SkipPHPString);
8010 }
8011 }
8012<*>\? {
8013 if (yyextra->insideCS && (YY_START != SkipRound) && (YY_START != CSAccessorDecl))
8014 {
8015 if (yyextra->current->type.empty())
8016 {
8017 if (yyextra->current->name.empty())
8018 yyextra->current->name="?";
8019 else
8020 yyextra->current->name+="?";
8021 }
8022 else
8023 {
8024 yyextra->current->type+="?";
8025 }
8026 }
8027 }
8028<*>"}" { yyextra->exported=false; }
8029<*>.
8030<SkipComment>{CPPC}|{CCS}
8031<*>{CCS} { yyextra->lastCContext = YY_START ;
8032 BEGIN( SkipComment ) ;
8033 }
8034<SkipComment>{B}*{CCE} { BEGIN( yyextra->lastCContext ) ; }
8035<*>{CPPC} {
8036 yyextra->lastCContext = YY_START ;
8037 BEGIN( SkipCxxComment ) ;
8038 }
8039<<EOF>> {
8040 if (yyextra->insideCS && yyextra->fakeNS)
8041 {
8042 yyextra->fakeNS--;
8043 unput('}');
8044 BEGIN ( ReadNSBody);
8045 }
8046 else
8047 {
8048 yyterminate();
8049 }
8050 }
8051%%
8052
8053//----------------------------------------------------------------------------
8054static int yyread(yyscan_t yyscanner,char *buf,int max_size)
8055{
8056 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8057 int c=0;
8058 while( c < max_size && yyextra->inputString[yyextra->inputPosition] )
8059 {
8060 *buf = yyextra->inputString[yyextra->inputPosition++] ;
8061 //printf("%d (%c)\n",*buf,*buf);
8062 c++; buf++;
8063 }
8064 return c;
8065}
8066
8067
8068static void initParser(yyscan_t yyscanner)
8069{
8070 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8071 yyextra->outerScopeEntries.clear();
8072 yyextra->baseName.clear();
8073 yyextra->protection = Protection::Public;
8074 yyextra->baseProt = Protection::Public;
8075 yyextra->sharpCount = 0;
8076 yyextra->roundCount = 0;
8077 yyextra->curlyCount = 0;
8078 yyextra->mtype = MethodTypes::Method;
8079 yyextra->isStatic = false;
8080 yyextra->virt = Specifier::Normal;
8081 yyextra->baseVirt = Specifier::Normal;
8082 yyextra->isTypedef = false;
8083 yyextra->insideTryBlock = false;
8084 yyextra->insideFormula = false;
8085 yyextra->insideCode=false;
8086 yyextra->insideCli=Config_getBool(CPP_CLI_SUPPORT);
8087 yyextra->previous = 0;
8088 yyextra->firstTypedefEntry.reset();
8089 yyextra->memspecEntry.reset();
8090}
8091
8092static void initEntry(yyscan_t yyscanner)
8093{
8094 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8095 if (yyextra->insideJava)
8096 {
8097 yyextra->protection = (yyextra->current_root->spec.isInterface() || yyextra->current_root->spec.isEnum()) ? Protection::Public : Protection::Package;
8098 }
8099 yyextra->current->protection = yyextra->protection;
8100 yyextra->current->exported = yyextra->exported ;
8101 yyextra->current->mtype = yyextra->mtype;
8102 yyextra->current->virt = yyextra->virt;
8103 yyextra->current->isStatic = yyextra->isStatic;
8104 yyextra->current->lang = yyextra->language;
8105 //printf("*** initEntry(yyscanner) yyextra->language=%d\n",yyextra->language);
8106 yyextra->commentScanner.initGroupInfo(yyextra->current.get());
8107 yyextra->isTypedef=false;
8108}
8109
8110
8111//-----------------------------------------------------------------------------
8112
8113static DString generateAnonymousAnchor(const DString &fileName,int count)
8114{
8115 DString fn = stripFromPath(fileName)+":"+DString().setNum(count);
8116 auto md5_sig = md5hash(fn.view());
8117 char result[md5_sig.size()*3+2];
8118 char *p = result;
8119 *p++='@';
8120 for (size_t i=0;i<md5_sig.size();i++)
8121 {
8122 static const char oct[]="01234567";
8123 uint8_t byte = md5_sig[i];
8124 *p++=oct[(byte>>6)&7];
8125 *p++=oct[(byte>>3)&7];
8126 *p++=oct[(byte>>0)&7];
8127 }
8128 *p='\0';
8129 return result;
8130}
8131
8132static void storeClangId(yyscan_t yyscanner,const char *id)
8133{
8134 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8135 if (yyextra->clangParser && (yyextra->insideCpp || yyextra->insideObjC))
8136 {
8137 yyextra->current->id = yyextra->clangParser->lookup(yyextra->yyLineNr,id);
8138 }
8139}
8140
8141static void lineCount(yyscan_t yyscanner)
8142{
8143 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8144 int tabSize = Config_getInt(TAB_SIZE);
8145 const char *p;
8146 for (p = yytext ; *p ; ++p )
8147 {
8148 if (*p=='\n')
8149 {
8150 yyextra->yyLineNr++;
8151 yyextra->column=0;
8152 yyextra->yyColNr=1;
8153 }
8154 else if (*p=='\t')
8155 {
8156 yyextra->column+=tabSize - (yyextra->column%tabSize);
8157 yyextra->yyColNr=1+yyextra->column;
8158 }
8159 else
8160 {
8161 yyextra->column++;
8162 yyextra->yyColNr++;
8163 }
8164 }
8165 //printf("lineCount()=%d\n",yyextra->column);
8166}
8167
8168static inline size_t computeIndent(const char *s,size_t startIndent)
8169{
8170 size_t col=startIndent;
8171 int tabSize=Config_getInt(TAB_SIZE);
8172 const char *p=s;
8173 char c;
8174 while ((c=*p++))
8175 {
8176 if (c=='\t') col+=tabSize-(col%tabSize);
8177 else if (c=='\n') col=0;
8178 else col++;
8179 }
8180 return col;
8181}
8182
8183static inline void initMethodProtection(yyscan_t yyscanner,Protection prot)
8184{
8185 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8186 yyextra->current->protection = yyextra->protection = prot;
8187 yyextra->current->mtype = yyextra->mtype = MethodTypes::Method;
8188 yyextra->current->type.clear();
8189 yyextra->current->name.clear();
8190 yyextra->current->args.clear();
8191 yyextra->current->argList.clear();
8192 lineCount(yyscanner) ;
8193}
8194
8195static void addType(yyscan_t yyscanner)
8196{
8197 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8198 size_t tl=yyextra->current->type.length();
8199 if( tl>0 && !yyextra->current->name.empty() && yyextra->current->type.at(tl-1)!='.')
8200 {
8201 yyextra->current->type += ' ' ;
8202 }
8203 yyextra->current->type += yyextra->current->name;
8204 yyextra->current->name.clear() ;
8205 tl=yyextra->current->type.length();
8206 if( tl>0 && !yyextra->current->args.empty() && yyextra->current->type.at(tl-1)!='.')
8207 {
8208 yyextra->current->type += ' ' ;
8209 }
8210 yyextra->current->type += yyextra->current->args ;
8211 yyextra->current->args.clear() ;
8212 yyextra->current->argList.clear();
8213}
8214
8215
8216static DString stripQuotes(const char *s)
8217{
8218 DString name;
8219 if (s==nullptr || *s==0) return name;
8220 name=s;
8221 if (name.at(0)=='"' && name.at(name.length()-1)=='"')
8222 {
8223 name=name.mid(1,name.length()-2);
8224 }
8225 return name;
8226}
8227
8228static DString stripFuncPtr(const DString &type)
8229{
8230 // we need to strip any trailing * and & (see bugs 623023 and 649103 for test cases)
8231 // also needed to reset the type for 'arr' to 'int' in 'typedef int (&fp)(), arr[2]'
8232 size_t i=type.length();
8233 bool funcPtr = i>0 && type[i-1]==')';
8234 if (funcPtr) i--;
8235 while (i>0 && (type[i-1]=='*' || type[i-1]=='&' || type[i-1]==' ')) i--;
8236 if (funcPtr && i>0 && type[i-1]=='(') i--;
8237 return type.left(i);
8238}
8239
8240//-----------------------------------------------------------------
8241static void startVerbatimBlock(yyscan_t yyscanner,const DString &blockName,size_t fencedSize,bool codeBlock)
8242{
8243 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8244 if (Config_getBool(MARKDOWN_SUPPORT))
8245 {
8246 yyextra->docBlock << "\\iskip";
8247 }
8248 yyextra->docBlockName=blockName;
8249 yyextra->fencedSize=fencedSize;
8250 yyextra->isCodeBlock=codeBlock;
8251 yyextra->nestedComment=0;
8252}
8253
8254//-----------------------------------------------------------------
8255static bool endVerbatimBlock(yyscan_t yyscanner,const DString &blockName,size_t fencedSize)
8256{
8257 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8258 if (yyextra->docBlockName==blockName && (fencedSize==0 || fencedSize==yyextra->fencedSize))
8259 {
8260 if (Config_getBool(MARKDOWN_SUPPORT))
8261 {
8262 yyextra->docBlock << "\\endiskip";
8263 }
8264 yyextra->docBlockName="";
8265 return true;
8266 }
8267 return false;
8268}
8269
8270//-----------------------------------------------------------------
8271
8272// return true iff req holds the start of a requires expression
8273// or sub-expression without parenthesis, i.e. req is empty or ends with || or &&
8274static bool startOfRequiresExpression(const DString &req)
8275{
8276 DString r = req.stripWhiteSpace();
8277 return r.empty() || r.endsWith("&&") || r.endsWith("||") || r.endsWith("and") || r.endsWith("or");
8278}
8279
8280//-----------------------------------------------------------------
8281
8282static bool nameIsOperator(DString &name)
8283{
8284 size_t i=name.find("operator");
8285 if (i==DString::npos) return false;
8286 if (i==0 && !isId(name.at(8))) return true; // case operator ::X
8287 if (i>0 && !isId(name.at(i-1)) && !isId(name.at(i+8))) return true; // case X::operator
8288 return false; // case TEXToperatorTEXT
8289}
8290
8291//-----------------------------------------------------------------------------
8292
8293static void setContext(yyscan_t yyscanner)
8294{
8295 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8296 yyextra->language = getLanguageFromFileName(yyextra->fileName);
8297 yyextra->insideIDL = yyextra->language==SrcLangExt::IDL;
8298 yyextra->insideJava = yyextra->language==SrcLangExt::Java;
8299 yyextra->insideCS = yyextra->language==SrcLangExt::CSharp;
8300 yyextra->insideD = yyextra->language==SrcLangExt::D;
8301 yyextra->insidePHP = yyextra->language==SrcLangExt::PHP;
8302 yyextra->insideObjC = yyextra->language==SrcLangExt::ObjC;
8303 yyextra->insideJS = yyextra->language==SrcLangExt::JS;
8304 yyextra->insideSlice = yyextra->language==SrcLangExt::Slice;
8305 yyextra->insideCpp = (yyextra->language==SrcLangExt::Cpp ||
8306 yyextra->language==SrcLangExt::Lex);
8307 //printf("setContext(%s) yyextra->insideIDL=%d yyextra->insideJava=%d yyextra->insideCS=%d "
8308 // "yyextra->insideD=%d yyextra->insidePHP=%d yyextra->insideObjC=%d\n",
8309 // qPrint(yyextra->fileName),yyextra->insideIDL,yyextra->insideJava,yyextra->insideCS,yyextra->insideD,yyextra->insidePHP,yyextra->insideObjC
8310 // );
8311}
8312
8313//-----------------------------------------------------------------------------
8314
8315static void prependScope(yyscan_t yyscanner)
8316{
8317 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8318 if (yyextra->current_root->section.isScope())
8319 {
8320 //printf("--- prependScope %s to %s\n",qPrint(yyextra->current_root->name),qPrint(yyextra->current->name));
8321 yyextra->current->name.prepend(yyextra->current_root->name+"::");
8322 //printf("prependScope #=%d #yyextra->current=%d\n",yyextra->current_root->tArgLists->count(),yyextra->current->tArgLists->count());
8323 for (const ArgumentList &srcAl : yyextra->current_root->tArgLists)
8324 {
8325 yyextra->current->tArgLists.insert(yyextra->current->tArgLists.begin(),srcAl);
8326 }
8327 }
8328}
8329
8330//-----------------------------------------------------------------------------
8331
8332/*! Returns true iff the yyextra->current entry could be a K&R style C function */
8333static bool checkForKnRstyleC(yyscan_t yyscanner)
8334{
8335 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8336 if (!yyextra->fileName.lower().endsWith(".c")) return false; // must be a C file
8337 if (yyextra->current->argList.empty()) return false; // must have arguments
8338 for (const Argument &a : yyextra->current->argList)
8339 {
8340 // in K&R style argument do not have a type, but doxygen expects a type
8341 // so it will think the argument has no name
8342 if (a.type.empty() || !a.name.empty()) return false;
8343 }
8344 return true;
8345}
8346
8347static void setJavaProtection(yyscan_t yyscanner)
8348{
8349 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8350 if (yyextra->insideJava)
8351 {
8352 DString text=yytext;
8353 yyextra->current->protection = Protection::Public;
8354 if (text.find("protected")!=DString::npos)
8355 yyextra->current->protection = Protection::Protected;
8356 else if (text.find("private")!=DString::npos)
8357 yyextra->current->protection = Protection::Private;
8358 else if (text.find("package")!=DString::npos)
8359 yyextra->current->protection = Protection::Package;
8360 }
8361}
8362//-----------------------------------------------------------------------------
8363
8364static void splitKnRArg(yyscan_t yyscanner,DString &oldStyleArgPtr,DString &oldStyleArgName)
8365{
8366 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8367 int si = static_cast<int>(yyextra->current->args.length());
8368 if (yyextra->oldStyleArgType.empty()) // new argument
8369 {
8370 std::string args = yyextra->current->args.str();
8371 static const reg::Ex re(R"(\‍([^)]*\).*)"); // find first (...)
8372 int bi1=-1;
8373 int bi2=-1;
8374 reg::Match match;
8375 if (reg::search(args,match,re))
8376 {
8377 bi1=(int)match.position();
8378 size_t secondMatchStart = match.position()+match.length(); // search again after first match
8379 if (reg::search(args,match,re,secondMatchStart))
8380 {
8381 bi2=(int)match.position();
8382 }
8383 }
8384 char c;
8385 if (bi1!=-1 && bi2!=-1) // found something like "int (*func)(int arg)"
8386 {
8387 int s=bi2+1; // keep opening (
8388 yyextra->oldStyleArgType = yyextra->current->args.left(s);
8389 int i=s;
8390 while (i<si && ((c=yyextra->current->args.at(i))=='*' || isspace((uint8_t)c))) i++;
8391 yyextra->oldStyleArgType += yyextra->current->args.mid(s,i-s);
8392 s=i;
8393 while (i<si && isId(yyextra->current->args.at(i))) i++;
8394 oldStyleArgName = yyextra->current->args.mid(s,i-s);
8395 yyextra->oldStyleArgType+=yyextra->current->args.mid(i);
8396 }
8397 else if (bi1!=-1) // redundant braces like in "int (*var)"
8398 {
8399 int s=bi1; // strip opening (
8400 yyextra->oldStyleArgType = yyextra->current->args.left(s);
8401 s++;
8402 int i=s+1;
8403 while (i<si && ((c=yyextra->current->args.at(i))=='*' || isspace((uint8_t)c))) i++;
8404 yyextra->oldStyleArgType += yyextra->current->args.mid(s,i-s);
8405 s=i;
8406 while (i<si && isId(yyextra->current->args.at(i))) i++;
8407 oldStyleArgName = yyextra->current->args.mid(s,i-s);
8408 }
8409 else // normal "int *var"
8410 {
8411 int l=si,i=l-1,j;
8412 // look for start of name in "type *name"
8413 while (i>=0 && isId(yyextra->current->args.at(i))) i--;
8414 j=i+1;
8415 // look for start of *'s
8416 while (i>=0 && ((c=yyextra->current->args.at(i))=='*' || isspace((uint8_t)c))) i--;
8417 i++;
8418 if (i!=l)
8419 {
8420 yyextra->oldStyleArgType=yyextra->current->args.left(i);
8421 oldStyleArgPtr=yyextra->current->args.mid(i,j-i);
8422 oldStyleArgName=yyextra->current->args.mid(j).stripWhiteSpace();
8423 }
8424 else
8425 {
8426 oldStyleArgName=yyextra->current->args.stripWhiteSpace();
8427 }
8428 }
8429 }
8430 else // continuation like *arg2 in "int *args,*arg2"
8431 {
8432 int l=si,j=0;
8433 char c;
8434 while (j<l && ((c=yyextra->current->args.at(j))=='*' || isspace((uint8_t)c))) j++;
8435 if (j>0)
8436 {
8437 oldStyleArgPtr=yyextra->current->args.left(j);
8438 oldStyleArgName=yyextra->current->args.mid(j).stripWhiteSpace();
8439 }
8440 else
8441 {
8442 oldStyleArgName=yyextra->current->args.stripWhiteSpace();
8443 }
8444 }
8445}
8446
8447//-----------------------------------------------------------------------------
8448
8449/*! Update the argument \a name with additional \a type info. For K&R style
8450 * function the type is found \e after the argument list, so this routine
8451 * in needed to fix up.
8452 */
8453static void addKnRArgInfo(yyscan_t yyscanner,const DString &type,const DString &name,
8454 const DString &brief,const DString &docs)
8455{
8456 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8457 for (Argument &a : yyextra->current->argList)
8458 {
8459 if (a.type==name)
8460 {
8461 a.type=type.stripWhiteSpace();
8462 a.type.stripPrefix("register ");
8463 a.name=name.stripWhiteSpace();
8464 if (!brief.empty() && !docs.empty())
8465 {
8466 a.docs=brief+"\n\n"+docs;
8467 }
8468 else if (!brief.empty())
8469 {
8470 a.docs=brief;
8471 }
8472 else
8473 {
8474 a.docs=docs;
8475 }
8476 }
8477 }
8478}
8479
8480//-----------------------------------------------------------------------------
8481
8483{
8484 for (Argument &a : al)
8485 {
8486 if (!a.type.empty() && a.name.empty())
8487 { // a->type is actually the (typeless) parameter name, so move it
8488 a.name=a.type;
8489 a.type.clear();
8490 }
8491 }
8492}
8493
8494//-----------------------------------------------------------------------------
8495
8496static void startCommentBlock(yyscan_t yyscanner,bool brief)
8497{
8498 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8499 if (brief)
8500 {
8501 yyextra->current->briefFile = yyextra->fileName;
8502 yyextra->current->briefLine = yyextra->yyLineNr;
8503 }
8504 else
8505 {
8506 yyextra->current->docFile = yyextra->fileName;
8507 yyextra->current->docLine = yyextra->yyLineNr;
8508 }
8509}
8510
8511//----------------------------------------------------------------------------
8512
8513static void newEntry(yyscan_t yyscanner)
8514{
8515 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8516 if (yyextra->tempEntry==0) // if temp entry is not 0, it holds yyextra->current,
8517 // and yyextra->current is actually replaced by yyextra->previous which was
8518 // already added to yyextra->current_root, so we should not add it again
8519 // (see bug723314)
8520 {
8521 yyextra->previous = yyextra->current;
8522 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
8523 }
8524 else
8525 {
8526 yyextra->previous = yyextra->current;
8527 yyextra->current = yyextra->tempEntry;
8528 yyextra->tempEntry.reset();
8529 }
8530 initEntry(yyscanner);
8531}
8532
8533static void handleCommentBlock(yyscan_t yyscanner,const DString &doc,bool brief)
8534{
8535 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8536 AUTO_TRACE("doc='{}' is_brief={}",Trace::trunc(doc),brief);
8537 bool hideInBodyDocs = Config_getBool(HIDE_IN_BODY_DOCS);
8538 if (yyextra->docBlockInBody && hideInBodyDocs) return;
8539 int lineNr = brief ? yyextra->current->briefLine : yyextra->current->docLine; // line of block start
8540
8541 // fill in inbodyFile && inbodyLine the first time, see bug 633891
8542 std::shared_ptr<Entry> docEntry = yyextra->docBlockInBody && yyextra->previous ? yyextra->previous : yyextra->current;
8543 if (yyextra->docBlockInBody && docEntry && docEntry->inbodyLine==-1)
8544 {
8545 docEntry->inbodyFile = yyextra->fileName;
8546 docEntry->inbodyLine = lineNr;
8547 }
8548
8549 int position=0;
8550 bool needsEntry=false;
8551 GuardedSectionStack guards;
8552 Markdown markdown(yyextra->fileName,lineNr);
8553 DString strippedDoc = stripIndentation(doc);
8554 DString processedDoc = Config_getBool(MARKDOWN_SUPPORT) ? markdown.process(strippedDoc,lineNr) : strippedDoc;
8555 while (yyextra->commentScanner.parseCommentBlock(
8556 yyextra->thisParser,
8557 yyextra->docBlockInBody && yyextra->previous ? yyextra->previous.get() : yyextra->current.get(),
8558 processedDoc, // text
8559 yyextra->fileName, // file
8560 lineNr, // line of block start
8561 yyextra->docBlockInBody ? false : brief, // isBrief
8562 yyextra->docBlockInBody ? false : yyextra->docBlockAutoBrief, // isJavaDocStyle
8563 yyextra->docBlockInBody, // isInBody
8564 yyextra->protection,
8565 position,
8566 needsEntry,
8567 Config_getBool(MARKDOWN_SUPPORT),
8568 &guards
8569 )
8570 )
8571 {
8572 //printf("parseCommentBlock position=%d [%s]\n",position,qPrint(doc)+position);
8573 if (needsEntry)
8574 {
8575 DString docFile = yyextra->current->docFile;
8576 newEntry(yyscanner);
8577 yyextra->current->docFile = docFile;
8578 yyextra->current->docLine = lineNr;
8579 }
8580 }
8581 if (needsEntry)
8582 {
8583 newEntry(yyscanner);
8584 }
8585
8586 if (yyextra->docBlockTerm)
8587 {
8588 unput(yyextra->docBlockTerm);
8589 yyextra->docBlockTerm=0;
8590 }
8591}
8592
8594{
8595 AUTO_TRACE();
8596 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8597 for (Argument &a : al)
8598 {
8599 AUTO_TRACE_ADD("Param '{}' docs='{}'",a.name,Trace::trunc(a.docs));
8600 if (!a.docs.empty())
8601 {
8602 if (a.name.empty() && a.type == "...") a.name= "...";
8603 int position=0;
8604 bool needsEntry;
8605
8606 // save context
8607 DString orgDoc = yyextra->current->doc;
8608 DString orgBrief = yyextra->current->brief;
8609 int orgDocLine = yyextra->current->docLine;
8610 int orgBriefLine = yyextra->current->briefLine;
8611
8612 yyextra->current->doc.clear();
8613 yyextra->current->brief.clear();
8614
8615 //printf("handleParametersCommentBlock [%s]\n",qPrint(doc));
8616 int lineNr = orgDocLine;
8617 GuardedSectionStack guards;
8618 Markdown markdown(yyextra->fileName,lineNr);
8619 DString strippedDoc = stripIndentation(a.docs);
8620 DString processedDoc = Config_getBool(MARKDOWN_SUPPORT) ? markdown.process(strippedDoc,lineNr) : strippedDoc;
8621 while (yyextra->commentScanner.parseCommentBlock(
8622 yyextra->thisParser,
8623 yyextra->current.get(),
8624 processedDoc, // text
8625 yyextra->fileName, // file
8626 lineNr,
8627 false,
8628 false,
8629 false,
8630 yyextra->protection,
8631 position,
8632 needsEntry,
8633 Config_getBool(MARKDOWN_SUPPORT),
8634 &guards
8635 )
8636 )
8637 {
8638 //printf("handleParametersCommentBlock position=%d [%s]\n",position,qPrint(doc)+position);
8639 if (needsEntry) newEntry(yyscanner);
8640 }
8641 if (needsEntry)
8642 {
8643 newEntry(yyscanner);
8644 }
8645 a.docs = yyextra->current->doc;
8646
8647 // restore context
8648 yyextra->current->doc = orgDoc;
8649 yyextra->current->brief = orgBrief;
8650 yyextra->current->docLine = orgDocLine;
8651 yyextra->current->briefLine = orgBriefLine;
8652 }
8653 }
8654}
8655
8656
8657//----------------------------------------------------------------------------
8658
8659static void parseCompounds(yyscan_t yyscanner,const std::shared_ptr<Entry> &rt)
8660{
8661 AUTO_TRACE("name={}",rt->name);
8662 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8663 for (const auto &ce : rt->children())
8664 {
8665 if (!ce->program.empty())
8666 {
8667 AUTO_TRACE_ADD("compound name='{}' program='{}'",Trace::trunc(ce->name),Trace::trunc(ce->program.str()));
8668 // init scanner state
8669 yyextra->padCount=0;
8670 yyextra->column=0;
8671 yyextra->programStr = ce->program.str();
8672 yyextra->inputString = yyextra->programStr.data();
8673 yyextra->inputPosition = 0;
8674 if (ce->section.isEnum() || ce->spec.isEnum())
8675 BEGIN( FindFields ) ;
8676 else
8677 BEGIN( FindMembers ) ;
8678 yyextra->current_root = ce;
8679 yyextra->fileName = ce->fileName;
8680 //setContext();
8681 yyextra->yyLineNr = ce->bodyLine;
8682 yyextra->yyColNr = ce->bodyColumn;
8683 yyextra->insideObjC = ce->lang==SrcLangExt::ObjC;
8684 //printf("---> Inner block starts at line %d objC=%d\n",yyextra->yyLineNr,yyextra->insideObjC);
8685 yyextra->current = std::make_shared<Entry>();
8686 yyextra->isStatic = false;
8687 initEntry(yyscanner);
8688
8689 // deep copy group list from parent (see bug 727732)
8690 bool autoGroupNested = Config_getBool(GROUP_NESTED_COMPOUNDS);
8691 if (autoGroupNested && !rt->groups.empty() && !ce->section.isEnum() && !ce->spec.isEnum())
8692 {
8693 ce->groups = rt->groups;
8694 }
8695
8696 size_t ni=ce->name.rfind("::");
8697 if (ni==DString::npos) ni=0; else ni+=2;
8698 // set default protection based on the compound type
8699 if ( ce->section.isClass() ) // class
8700 {
8701 if (yyextra->insidePHP || yyextra->insideD || yyextra->insideJS || yyextra->insideIDL || yyextra->insideSlice)
8702 {
8703 yyextra->current->protection = yyextra->protection = Protection::Public ;
8704 }
8705 else if (yyextra->insideJava)
8706 {
8707 yyextra->current->protection = yyextra->protection = (ce->spec.isInterface() || ce->spec.isEnum()) ? Protection::Public : Protection::Package;
8708 }
8709 else if (ce->spec.isInterface() || ce->spec.isRef() || ce->spec.isValue() || ce->spec.isStruct() || ce->spec.isUnion())
8710 {
8711 if (ce->lang==SrcLangExt::ObjC)
8712 {
8713 yyextra->current->protection = yyextra->protection = Protection::Protected ;
8714 }
8715 else
8716 {
8717 yyextra->current->protection = yyextra->protection = Protection::Public ;
8718 }
8719 }
8720 else
8721 {
8722 yyextra->current->protection = yyextra->protection = Protection::Private ;
8723 }
8724 }
8725 else if (ce->section.isEnum() ) // enum
8726 {
8727 yyextra->current->protection = yyextra->protection = ce->protection;
8728 }
8729 else if (!ce->name.empty() && ce->name.at(ni)=='@') // unnamed union or namespace
8730 {
8731 if (ce->section.isNamespace() ) // unnamed namespace
8732 {
8733 yyextra->current->isStatic = yyextra->isStatic = true;
8734 }
8735 yyextra->current->protection = yyextra->protection = ce->protection;
8736 yyextra->current->exported = yyextra->exported = false;
8737 }
8738 else if (ce->section.isNamespace() )
8739 {
8740 yyextra->current->protection = yyextra->protection = Protection::Public ;
8741 yyextra->current->exported = yyextra->exported = ce->exported;
8742 }
8743 else // named struct, union, protocol, category
8744 {
8745 yyextra->current->protection = yyextra->protection = Protection::Public ;
8746 yyextra->current->exported = yyextra->exported = false;
8747 }
8748 yyextra->mtype = MethodTypes::Method;
8749 yyextra->virt = Specifier::Normal;
8750 //printf("name=%s yyextra->current->isStatic=%d yyextra->isStatic=%d\n",qPrint(ce->name),yyextra->current->isStatic,yyextra->isStatic);
8751
8752 //memberGroupId = DOX_NOGROUP;
8753 //memberGroupRelates.clear();
8754 //memberGroupInside.clear();
8755 DString name = ce->name;
8756 yyextra->commentScanner.enterCompound(yyextra->fileName,yyextra->yyLineNr,name);
8757
8758 scannerYYlex(yyscanner);
8759 //forceEndGroup();
8760
8761 yyextra->commentScanner.leaveCompound(yyextra->fileName,yyextra->yyLineNr,name);
8762
8763 yyextra->programStr.clear();
8764 ce->program.str(std::string());
8765
8766
8767 //if (depthIf>0)
8768 //{
8769 // warn(yyextra->fileName,yyextra->yyLineNr,"Documentation block ended in the middle of a conditional section!");
8770 //}
8771 }
8772 parseCompounds(yyscanner,ce);
8773 }
8774}
8775
8776static void parseConcepts(yyscan_t yyscanner,const std::shared_ptr<Entry> &rt)
8777{
8778 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8779 for (const auto &ce : rt->children())
8780 {
8781 if (ce->section.isConcept())
8782 {
8783 //printf("*** found concept '%s' value=[[\n%s\n]] line=%d,col=%d\n",
8784 // qPrint(ce->name),qPrint(ce->initializer.str()),ce->startLine,ce->startColumn);
8785 yyextra->commentScanner.enterCompound(yyextra->fileName,yyextra->yyLineNr,ce->name);
8786 // init scanner state
8787 yyextra->padCount =0;
8788 yyextra->column =0;
8789 yyextra->programStr = ce->initializer.str();
8790 yyextra->inputString = yyextra->programStr.data();
8791 yyextra->inputPosition = 0;
8792 yyextra->current_root = ce;
8793 yyextra->fileName = ce->fileName;
8794 yyextra->yyLineNr = ce->bodyLine;
8795 yyextra->yyColNr = ce->bodyColumn;
8796 yyextra->insideObjC = false;
8797 yyextra->current = std::make_shared<Entry>();
8798
8799 // hack to reconstruct what was in the code before the concept expression
8800 DString indent;
8801 indent.fill(' ',ce->startColumn?ce->startColumn-1:0);
8802 DString templArgs;
8803 if (!ce->args.empty())
8804 {
8805 templArgs=indent+"template"+ce->args+"\n";
8806 }
8807 yyextra->current->initializer.str(DString(templArgs+indent+"concept "+ce->name+ " =").str());
8808
8809 yyextra->isStatic = false;
8810 initEntry(yyscanner);
8811 yyextra->current->section = EntryType::makeConceptCodePart();
8812 yyextra->current->startLine = yyextra->yyLineNr;
8813 BEGIN( FindConceptParts );
8814 scannerYYlex(yyscanner);
8815 yyextra->commentScanner.leaveCompound(yyextra->fileName,yyextra->yyLineNr,ce->name);
8816
8817 }
8818 parseConcepts(yyscanner,ce);
8819 }
8820}
8821
8822//----------------------------------------------------------------------------
8823
8824static void parseMain(yyscan_t yyscanner,
8825 const DString &fileName,
8826 const char *fileBuf,
8827 const std::shared_ptr<Entry> &rt,
8828 ClangTUParser *clangParser)
8829{
8830 AUTO_TRACE("fileName={}",fileName);
8831 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8832 initParser(yyscanner);
8833
8834 yyextra->inputString = fileBuf;
8835 yyextra->inputPosition = 0;
8836 yyextra->column = 0;
8837 scannerYYrestart(nullptr,yyscanner);
8838
8839 //depthIf = 0;
8840 yyextra->protection = Protection::Public;
8841 yyextra->mtype = MethodTypes::Method;
8842 yyextra->isStatic = false;
8843 yyextra->exported = false;
8844 yyextra->virt = Specifier::Normal;
8845 yyextra->current_root = rt;
8846 yyextra->yyLineNr = 1 ;
8847 yyextra->yyBegLineNr = 1;
8848 yyextra->yyBegColNr = 0;
8849 yyextra->anonCount = 0;
8850 yyextra->anonNSCount = 0;
8851 yyextra->fileName = fileName;
8852 yyextra->clangParser = clangParser;
8853 setContext(yyscanner);
8854 rt->lang = yyextra->language;
8855 msg("Parsing file {}...\n",yyextra->fileName);
8856
8857 yyextra->current_root = rt;
8858 initParser(yyscanner);
8859 yyextra->commentScanner.enterFile(yyextra->fileName,yyextra->yyLineNr);
8860 yyextra->current = std::make_shared<Entry>();
8861 //printf("yyextra->current=%p yyextra->current_root=%p\n",yyextra->current,yyextra->current_root);
8862 EntryType sec=EntryType::guessSection(yyextra->fileName);
8863 if (!sec.isEmpty())
8864 {
8865 yyextra->current->name = yyextra->fileName;
8866 yyextra->current->section = sec;
8867 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
8868 }
8869 yyextra->current->reset();
8870 initEntry(yyscanner);
8871 if ( yyextra->insidePHP )
8872 {
8873 BEGIN( FindMembersPHP );
8874 }
8875 else if ( yyextra->insideJava ) // add default java.lang package scope
8876 {
8877 yyextra->current->name="java::lang"; // '::' is used in doxygen's internal representation as a scope separator
8878 yyextra->current->fileName = yyextra->fileName;
8879 yyextra->current->section = EntryType::makeUsingDir();
8880 yyextra->current_root->moveToSubEntryAndRefresh(yyextra->current);
8881 initEntry(yyscanner);
8882 BEGIN( FindMembers );
8883 }
8884 else
8885 {
8886 BEGIN( FindMembers );
8887 }
8888
8889 scannerYYlex(yyscanner);
8890
8891 if (YY_START==Comment)
8892 {
8893 warn(yyextra->fileName,yyextra->yyLineNr,"File ended in the middle of a comment block! Perhaps a missing \\endcode?");
8894 }
8895
8896 //forceEndGroup();
8897 yyextra->commentScanner.leaveFile(yyextra->fileName,yyextra->yyLineNr);
8898
8899 yyextra->programStr.clear();
8900 rt->program.str(std::string());
8901
8902 parseCompounds(yyscanner,rt);
8903 parseConcepts(yyscanner,rt);
8904
8905 yyextra->anonNSCount++;
8906
8907 // add additional entries that were created during processing
8908 for (auto &[parent,child]: yyextra->outerScopeEntries)
8909 {
8910 //printf(">>> adding '%s' to scope '%s'\n",qPrint(child->name),qPrint(parent->name));
8911 parent->moveToSubEntryAndKeep(child);
8912 }
8913 yyextra->outerScopeEntries.clear();
8914
8915}
8916
8917//----------------------------------------------------------------------------
8918
8919static void parsePrototype(yyscan_t yyscanner,const DString &text)
8920{
8921 AUTO_TRACE("text='{}'",Trace::trunc(text));
8922 struct yyguts_t *yyg = (struct yyguts_t*)yyscanner;
8923 if (text.empty())
8924 {
8925 warn(yyextra->fileName,yyextra->yyLineNr,"Empty prototype found!");
8926 return;
8927 }
8928 if (!yyextra->current) // nothing to store (see bug683516)
8929 {
8930 return;
8931 }
8932
8933 const char *orgInputString;
8934 int orgInputPosition;
8935 YY_BUFFER_STATE orgState;
8936
8937 // save scanner state
8938 orgState = YY_CURRENT_BUFFER;
8939 yy_switch_to_buffer(yy_create_buffer(nullptr, YY_BUF_SIZE, yyscanner), yyscanner);
8940 orgInputString = yyextra->inputString;
8941 orgInputPosition = yyextra->inputPosition;
8942
8943 // set new string
8944 yyextra->inputString = text.data();
8945 yyextra->inputPosition = 0;
8946 yyextra->column = 0;
8947 scannerYYrestart(nullptr, yyscanner);
8948 BEGIN(Prototype);
8949 scannerYYlex(yyscanner);
8950
8951 yyextra->current->name = yyextra->current->name.stripWhiteSpace();
8952 if (yyextra->current->section.isMemberDoc() && yyextra->current->args.empty())
8953 {
8954 yyextra->current->section = EntryType::makeVariableDoc();
8955 }
8956
8957 // restore original scanner state
8958 yy_delete_buffer(YY_CURRENT_BUFFER, yyscanner);
8959 yy_switch_to_buffer(orgState, yyscanner);
8960 yyextra->inputString = orgInputString;
8961 yyextra->inputPosition = orgInputPosition;
8962
8963
8964 //printf("**** parsePrototype end\n");
8965}
8966
8967//----------------------------------------------------------------------------
8968
8974
8976{
8977 scannerYYlex_init_extra(&p->state,&p->yyscanner);
8978#ifdef FLEX_DEBUG
8979 scannerYYset_debug(Debug::isFlagSet(Debug::Lex_scanner)?1:0,p->yyscanner);
8980#endif
8981}
8982
8984{
8985 scannerYYlex_destroy(p->yyscanner);
8986}
8987
8989 const char *fileBuf,
8990 const std::shared_ptr<Entry> &root,
8991 ClangTUParser *clangParser)
8992{
8993 AUTO_TRACE();
8994 struct yyguts_t *yyg = (struct yyguts_t*)p->yyscanner;
8995 yyextra->thisParser = this;
8996
8997 DebugLex debugLex(Debug::Lex_scanner, __FILE__, qPrint(fileName));
8998
8999 ::parseMain(p->yyscanner,fileName,fileBuf,root,clangParser);
9000}
9001
9002
9004{
9005 DString fe=extension.lower();
9006 SrcLangExt lang = getLanguageFromFileName(extension);
9007 return (SrcLangExt::Cpp == lang) || (SrcLangExt::Lex == lang) ||
9008 !( fe==".java" || fe==".as" || fe==".d" || fe==".php" ||
9009 fe==".php4" || fe==".inc" || fe==".phtml"|| fe==".php5"
9010 );
9011}
9012
9014{
9015 ::parsePrototype(p->yyscanner,text);
9016}
9017
9018//----------------------------------------------------------------------------
9019
9020#include "scanner.l.h"
DString docs
Definition arguments.h:48
DString name
Definition arguments.h:45
void parsePrototype(const DString &text) override
Callback function called by the comment block scanner.
Definition scanner.l:9013
bool needsPreprocessing(const DString &extension) const override
Returns true if the language identified by extension needs the C preprocessor to be run before feed t...
Definition scanner.l:9003
void parseInput(const DString &fileName, const char *fileBuf, const std::shared_ptr< Entry > &root, ClangTUParser *clangParser) override
Parses a single input file with the goal to build an Entry tree.
Definition scanner.l:8988
std::unique_ptr< Private > p
Definition scanner.h:44
~COutlineParser() override
Definition scanner.l:8983
DString & setNum(short n)
Definition dstring.h:556
DString lower() const
Definition dstring.h:330
std::string_view view() const
Definition dstring.h:166
bool stripPrefix(const DString &prefix)
Definition dstring.h:294
const char * data() const
Returns a pointer to the contents of the string in the form of a 0-terminated C string.
Definition dstring.h:161
bool endsWith(const char *s) const
Definition dstring.h:621
@ Lex_scanner
Definition debug.h:69
static bool isFlagSet(const DebugMask mask)
Definition debug.cpp:132
Protection protection
class protection
Definition entry.h:179
static EntryType guessSection(const DString &name)
Definition types.cpp:22
Helper class to process markdown formatted text.
Definition markdown.h:33
DString process(const DString &input, int &startNewlines, bool fromParseInput=false)
static int yyread(yyscan_t yyscanner, char *buf, int max_size)
#define YY_BUF_SIZE
Definition commentcnv.l:19
std::stack< GuardedSection > GuardedSectionStack
Definition commentscan.h:48
#define Config_getInt(name)
Definition config.h:34
#define AUTO_TRACE_ADD(...)
Definition docnode.cpp:54
#define AUTO_TRACE(...)
Definition docnode.cpp:53
constexpr DocNodeVariant * parent(DocNodeVariant *n)
returns the parent node of a given node n or nullptr if the node has no parent.
Definition docnode.h:1335
const char * qPrint(const char *s)
Definition dstring.h:787
std::array< uint8_t, 16 > md5hash(const std::string_view &str)
Definition md5hash.h:26
#define msg(fmt,...)
Definition message.h:94
DString trunc(const DString &s, size_t numChars=15)
Definition trace.h:56
Definition dstring.h:917
static void newEntry(yyscan_t yyscanner)
Definition scanner.l:8513
static void parseMain(yyscan_t yyscanner, const DString &fileName, const char *fileBuf, const std::shared_ptr< Entry > &rt, ClangTUParser *clangParser)
Definition scanner.l:8824
static void parseCompounds(yyscan_t yyscanner, const std::shared_ptr< Entry > &rt)
Definition scanner.l:8659
static void parsePrototype(yyscan_t yyscanner, const DString &text)
Definition scanner.l:8919
static void parseConcepts(yyscan_t yyscanner, const std::shared_ptr< Entry > &rt)
Definition scanner.l:8776
scannerYY_state state
Definition scanner.l:8972
SrcLangExt getLanguageFromFileName(const DString &fileName, SrcLangExt defLang)
Definition util.cpp:4169
DString stripIndentation(const DString &s, bool skipFirstLine)
Definition util.cpp:4684
DString stripFromPath(const DString &path)
Definition util.cpp:220