|
1 /****************************************************************************** |
|
2 * |
|
3 * Copyright (C) 1997-2008 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 /****************************************************************************** |
|
16 * Parser for syntax hightlighting and references for vhdl subset |
|
17 * written by M. Kreis |
|
18 * supports VHDL-87 |
|
19 * does not support VHDL-AMS |
|
20 ******************************************************************************/ |
|
21 |
|
22 %{ |
|
23 |
|
24 /* |
|
25 * includes |
|
26 */ |
|
27 #include <stdio.h> |
|
28 #include <assert.h> |
|
29 #include <ctype.h> |
|
30 #include <qregexp.h> |
|
31 #include <qdir.h> |
|
32 #include <qstringlist.h> |
|
33 |
|
34 #include "qtbc.h" |
|
35 #include "entry.h" |
|
36 #include "doxygen.h" |
|
37 #include "message.h" |
|
38 #include "outputlist.h" |
|
39 #include "util.h" |
|
40 #include "membername.h" |
|
41 #include "searchindex.h" |
|
42 #include "vhdldocgen.h" |
|
43 |
|
44 #define YY_NEVER_INTERACTIVE 1 |
|
45 |
|
46 // Toggle for some debugging info |
|
47 //#define DBG_CTX(x) fprintf x |
|
48 #define DBG_CTX(x) do { } while(0) |
|
49 |
|
50 |
|
51 /* ----------------------------------------------------------------- |
|
52 * statics |
|
53 */ |
|
54 |
|
55 // ----------------- <vhdl> ---------------------------------- |
|
56 |
|
57 //static bool isPackBody=FALSE; |
|
58 //static bool isStartMap; |
|
59 static bool isFuncProto=FALSE; |
|
60 static bool isComponent=FALSE; |
|
61 static bool isPackageBody=FALSE; |
|
62 static bool isProto = FALSE; |
|
63 |
|
64 static QCString g_PrevString; |
|
65 static QCString g_CurrClass; |
|
66 static QDict<QCString>g_vhdlKeyDict; |
|
67 static QCString g_tempClass; |
|
68 static QCString g_tempComp; |
|
69 static QCString g_PortMapComp; |
|
70 static MemberDef *g_vhdlMember; |
|
71 static QCString g_FuncProto; |
|
72 |
|
73 //----------------------------------------------------------- |
|
74 |
|
75 static CodeOutputInterface * g_code; |
|
76 static QCString g_curClassName; |
|
77 static QCString g_parmType; |
|
78 static QCString g_parmName; |
|
79 static const char * g_inputString; //!< the code fragment as text |
|
80 static int g_inputPosition; //!< read offset during parsing |
|
81 static int g_inputLines; //!< number of line in the code fragment |
|
82 static int g_yyLineNr; //!< current line number |
|
83 static bool g_needsTermination; |
|
84 |
|
85 static QCString g_exampleName; |
|
86 static QCString g_exampleFile; |
|
87 |
|
88 static QCString g_type; |
|
89 static QCString g_name; |
|
90 static QCString g_args; |
|
91 static QCString g_classScope; |
|
92 |
|
93 static QCString g_CurrScope; |
|
94 |
|
95 static FileDef * g_sourceFileDef; |
|
96 static Definition * g_currentDefinition; |
|
97 static MemberDef * g_currentMemberDef; |
|
98 static bool g_includeCodeFragment; |
|
99 static const char * g_currentFontClass; |
|
100 |
|
101 static bool g_lexInit = FALSE; |
|
102 static int g_braceCount=0; |
|
103 |
|
104 |
|
105 static void writeFont(const char *s,const char* text); |
|
106 static void generateMemLink(CodeOutputInterface &ol,QCString &clName,QCString& memberName); |
|
107 static bool writeColoredWord(QCString& word ); |
|
108 static void generateClassOrGlobalLink(CodeOutputInterface &ol,const char *clName, bool typeOnly=FALSE); |
|
109 static void endFontClass(); |
|
110 static void startFontClass(const char *s); |
|
111 //------------------------------------------------------------------- |
|
112 |
|
113 |
|
114 static void setCurrentDoc(const QCString &name,const QCString &base,const QCString &anchor="") |
|
115 { |
|
116 if (Doxygen::searchIndex) |
|
117 { |
|
118 Doxygen::searchIndex->setCurrentDoc(name,base,anchor); |
|
119 } |
|
120 } |
|
121 |
|
122 static bool checkString(QCString &name) |
|
123 { |
|
124 if (name.isEmpty()) return FALSE; |
|
125 static QRegExp regg("[\\s\"]"); |
|
126 |
|
127 int len=name.length(); |
|
128 if (name.at(0)=='"' && name.at(len-1)=='"' && len > 2) |
|
129 { |
|
130 QStringList qrl=QStringList::split(regg,name,FALSE); |
|
131 if (VhdlDocGen::isNumber((QCString)qrl[0])) |
|
132 { |
|
133 g_code->codify("\""); |
|
134 startFontClass("vhdllogic"); |
|
135 QCString mid=name.mid(1,len-2); //" 1223 " |
|
136 g_code->codify(mid.data()); |
|
137 endFontClass(); |
|
138 g_code->codify("\""); |
|
139 } |
|
140 else |
|
141 { |
|
142 startFontClass("keyword"); |
|
143 g_code->codify(name.data()); |
|
144 endFontClass(); |
|
145 } |
|
146 return TRUE; |
|
147 } |
|
148 |
|
149 if (VhdlDocGen::isNumber(name)) |
|
150 { |
|
151 startFontClass("vhdllogic"); |
|
152 g_code->codify(name.data()); |
|
153 endFontClass(); |
|
154 return TRUE; |
|
155 } |
|
156 return FALSE; |
|
157 } |
|
158 |
|
159 static void addToSearchIndex(const char *text) |
|
160 { |
|
161 if (Doxygen::searchIndex) |
|
162 { |
|
163 Doxygen::searchIndex->addWord(text,FALSE); |
|
164 } |
|
165 } |
|
166 |
|
167 |
|
168 /*! start a new line of code, inserting a line number if g_sourceFileDef |
|
169 * is TRUE. If a definition starts at the current line, then the line |
|
170 * number is linked to the documentation of that definition. |
|
171 */ |
|
172 static void startCodeLine() |
|
173 { |
|
174 //if (g_currentFontClass) { g_code->endFontClass(); } |
|
175 if (g_sourceFileDef) |
|
176 { |
|
177 //QCString lineNumber,lineAnchor; |
|
178 //lineNumber.sprintf("%05d",g_yyLineNr); |
|
179 //lineAnchor.sprintf("l%05d",g_yyLineNr); |
|
180 // if ((g_yyLineNr % 500) == 0) |
|
181 // fprintf(stderr,"\n starting Line %d:",g_yyLineNr); |
|
182 Definition *d = g_sourceFileDef->getSourceDefinition(g_yyLineNr); |
|
183 //printf("startCodeLine %d d=%s\n", g_yyLineNr,d ? d->name().data() : "<null>"); |
|
184 if (!g_includeCodeFragment && d) |
|
185 { |
|
186 g_currentDefinition = d; |
|
187 g_currentMemberDef = g_sourceFileDef->getSourceMember(g_yyLineNr); |
|
188 if (!g_tempComp.isEmpty() && g_currentMemberDef ) |
|
189 { |
|
190 //ClassDef *cf=VhdlDocGen::getClass(g_tempComp.data()); |
|
191 QCString nn=g_currentMemberDef->name(); |
|
192 MemberDef* mdeff=VhdlDocGen::findMember(g_tempComp,nn); |
|
193 if (mdeff) |
|
194 { |
|
195 g_currentMemberDef=mdeff; |
|
196 } |
|
197 } |
|
198 |
|
199 g_parmType.resize(0); |
|
200 g_parmName.resize(0); |
|
201 QCString lineAnchor; |
|
202 lineAnchor.sprintf("l%05d",g_yyLineNr); |
|
203 if (g_currentMemberDef) |
|
204 { |
|
205 g_code->writeLineNumber(g_currentMemberDef->getReference(), |
|
206 g_currentMemberDef->getOutputFileBase(), |
|
207 g_currentMemberDef->anchor(),g_yyLineNr); |
|
208 setCurrentDoc(g_currentMemberDef->qualifiedName(), |
|
209 g_sourceFileDef->getSourceFileBase(), |
|
210 lineAnchor); |
|
211 } |
|
212 else if (d->isLinkableInProject()) |
|
213 { |
|
214 g_code->writeLineNumber(d->getReference(), |
|
215 d->getOutputFileBase(), |
|
216 0,g_yyLineNr); |
|
217 setCurrentDoc(d->qualifiedName(), |
|
218 g_sourceFileDef->getSourceFileBase(), |
|
219 lineAnchor); |
|
220 } |
|
221 } |
|
222 else |
|
223 { |
|
224 g_code->writeLineNumber(0,0,0,g_yyLineNr); |
|
225 } |
|
226 } |
|
227 g_code->startCodeLine(); |
|
228 if (g_currentFontClass) |
|
229 { |
|
230 g_code->startFontClass(g_currentFontClass); |
|
231 } |
|
232 } |
|
233 |
|
234 static void endFontClass(); |
|
235 static void endCodeLine() |
|
236 { |
|
237 endFontClass(); |
|
238 g_code->endCodeLine(); |
|
239 } |
|
240 |
|
241 static void nextCodeLine() |
|
242 { |
|
243 const char *fc = g_currentFontClass; |
|
244 endCodeLine(); |
|
245 if (g_yyLineNr<g_inputLines) |
|
246 { |
|
247 g_currentFontClass = fc; |
|
248 startCodeLine(); |
|
249 } |
|
250 } |
|
251 |
|
252 /*! writes a word to the output. |
|
253 * If curr_class is defined, the word belongs to a class |
|
254 * and will be linked. |
|
255 */ |
|
256 |
|
257 static void writeWord(const char *word,const char* curr_class=0,bool classLink=FALSE) |
|
258 { |
|
259 bool found=FALSE; |
|
260 QCString temp; |
|
261 QCString tclass(curr_class); |
|
262 QCString ttt(word); |
|
263 if (ttt.isEmpty()) return; |
|
264 for (unsigned int j=0;j<ttt.length();j++) |
|
265 { |
|
266 char c=ttt.at(j); |
|
267 if (c==' '|| c==',' || c==';' || c==':' || c=='(' || c==')' || c=='\r' || c=='\t' || c=='.') |
|
268 { |
|
269 if (found) |
|
270 { |
|
271 if (!writeColoredWord(temp)) // is it a keyword ? |
|
272 { |
|
273 //if (VhdlDocGen::findKeyWord(temp)) |
|
274 // writeFont("vhdlkeyword",temp.data()); |
|
275 //printf("writeWord: %s\n",temp.data()); |
|
276 if (!tclass.isEmpty()) |
|
277 { |
|
278 if (!classLink) |
|
279 { |
|
280 generateMemLink(*g_code,tclass,temp); |
|
281 } |
|
282 else |
|
283 { |
|
284 generateClassOrGlobalLink(*g_code,temp); |
|
285 } |
|
286 } |
|
287 else |
|
288 { |
|
289 if (!checkString(temp)) |
|
290 g_code->codify(temp.data()); |
|
291 } |
|
292 } |
|
293 temp.resize(0); |
|
294 found=FALSE; |
|
295 } |
|
296 |
|
297 char cc[2]; |
|
298 cc[0]=c; |
|
299 cc[1]=0; |
|
300 g_code->codify(cc); |
|
301 } |
|
302 else |
|
303 { |
|
304 found=TRUE; |
|
305 temp+=c; |
|
306 } |
|
307 } // for |
|
308 |
|
309 if (!temp.isEmpty()) |
|
310 { |
|
311 if (!writeColoredWord(temp)) |
|
312 { |
|
313 if (!tclass.isEmpty()) |
|
314 { |
|
315 if (!classLink) |
|
316 { |
|
317 generateMemLink(*g_code,tclass,temp); // generateMemLink(*g_code,g_CurrClass,left); |
|
318 } |
|
319 else |
|
320 { |
|
321 generateClassOrGlobalLink(*g_code,temp); |
|
322 } |
|
323 } |
|
324 else |
|
325 { |
|
326 QCString qc(temp.data()); |
|
327 if (VhdlDocGen::isNumber(qc)){ |
|
328 startFontClass("vhdllogic"); |
|
329 g_code->codify(temp.data()); |
|
330 endFontClass(); |
|
331 } |
|
332 else |
|
333 g_code->codify(temp.data()); |
|
334 } |
|
335 } |
|
336 } |
|
337 }// writeWord |
|
338 |
|
339 |
|
340 /*! write a code fragment `text' that may span multiple lines, inserting |
|
341 * line numbers for each line. |
|
342 */ |
|
343 static void codifyLines(const char *text,const char *cl=0,bool classlink=FALSE) |
|
344 { |
|
345 if (text==0) return; |
|
346 //printf("codifyLines(%d,\"%s\")\n",g_yyLineNr,text); |
|
347 const char *p=text,*sp=p; |
|
348 char c; |
|
349 bool done=FALSE; |
|
350 while (!done) |
|
351 { |
|
352 sp=p; |
|
353 while ((c=*p++) && c!='\n') {} |
|
354 if (c=='\n') |
|
355 { |
|
356 g_yyLineNr++; |
|
357 QCString line = sp; |
|
358 line = line.left(p-sp-1); |
|
359 //*(p-1)='\0'; |
|
360 //g_code->codify(sp); |
|
361 writeWord(line,cl,classlink); |
|
362 nextCodeLine(); |
|
363 } |
|
364 else |
|
365 { |
|
366 //g_code->codify(sp); |
|
367 writeWord(sp,cl,classlink); |
|
368 done=TRUE; |
|
369 } |
|
370 } |
|
371 } |
|
372 |
|
373 /*! writes a link to a fragment \a text that may span multiple lines, inserting |
|
374 * line numbers for each line. If \a text contains newlines, the link will be |
|
375 * split into multiple links with the same destination, one for each line. |
|
376 */ |
|
377 static void writeMultiLineCodeLink(CodeOutputInterface &ol, |
|
378 const char *ref,const char *file, |
|
379 const char *anchor,const char *text, |
|
380 const char *tooltip) |
|
381 { |
|
382 bool done=FALSE; |
|
383 char *p=(char *)text; |
|
384 while (!done) |
|
385 { |
|
386 char *sp=p; |
|
387 char c; |
|
388 while ((c=*p++) && c!='\n') {} |
|
389 if (c=='\n') |
|
390 { |
|
391 g_yyLineNr++; |
|
392 *(p-1)='\0'; |
|
393 // printf("writeCodeLink(%s,%s,%s,%s)\n",ref,file,anchor,sp); |
|
394 ol.writeCodeLink(ref,file,anchor,sp,tooltip); |
|
395 nextCodeLine(); |
|
396 } |
|
397 else |
|
398 { |
|
399 ol.writeCodeLink(ref,file,anchor,sp,tooltip); |
|
400 done=TRUE; |
|
401 } |
|
402 } |
|
403 } |
|
404 |
|
405 static void setParameterList(MemberDef *md) |
|
406 { |
|
407 g_classScope = md->getClassDef() ? md->getClassDef()->name().data() : ""; |
|
408 LockingPtr<ArgumentList> al = md->argumentList(); |
|
409 if (al==0) return; |
|
410 Argument *a = al->first(); |
|
411 while (a) |
|
412 { |
|
413 g_parmName = a->name.copy(); |
|
414 g_parmType = a->type.copy(); |
|
415 int i = g_parmType.find('*'); |
|
416 if (i!=-1) g_parmType = g_parmType.left(i); |
|
417 i = g_parmType.find('&'); |
|
418 if (i!=-1) g_parmType = g_parmType.left(i); |
|
419 g_parmType.stripPrefix("const "); |
|
420 g_parmType=g_parmType.stripWhiteSpace(); |
|
421 // g_theVarContext.addVariable(g_parmType,g_parmName); |
|
422 a = al->next(); |
|
423 } |
|
424 } |
|
425 |
|
426 |
|
427 /*! writes a link to a function or procedure |
|
428 */ |
|
429 |
|
430 static void generateFuncLink(CodeOutputInterface &ol,MemberDef* mdef) |
|
431 { |
|
432 |
|
433 //printf("generateFuncLink(FuncName=%s)\n",mdef->name().data()); |
|
434 QCString memberName=mdef->name(); |
|
435 |
|
436 if (mdef && mdef->isLinkable()) // is it a linkable class |
|
437 { |
|
438 writeMultiLineCodeLink(ol,mdef->getReference(), |
|
439 mdef->getOutputFileBase(), |
|
440 mdef->anchor(), |
|
441 mdef->name(), |
|
442 mdef->briefDescriptionAsTooltip()); |
|
443 addToSearchIndex(memberName); |
|
444 return; |
|
445 } |
|
446 ol.linkableSymbol(g_yyLineNr,memberName,0,g_currentMemberDef?g_currentMemberDef:g_currentDefinition); |
|
447 codifyLines(memberName.data()); |
|
448 addToSearchIndex(memberName); |
|
449 } // generateFuncLink |
|
450 |
|
451 |
|
452 static void generateMemLink(CodeOutputInterface &ol,QCString &clName,QCString& memberName) |
|
453 { |
|
454 if (clName.isEmpty() || memberName.isEmpty()) return; |
|
455 QCString className=clName; |
|
456 |
|
457 MemberDef *md=0; |
|
458 //MemberDef *comp=0; |
|
459 //bool isLocal=FALSE; |
|
460 |
|
461 md=VhdlDocGen::findMember(className,memberName); |
|
462 ClassDef *po=VhdlDocGen::getClass(className.data()); |
|
463 |
|
464 if (md==0 && po && (VhdlDocGen::VhdlClasses)po->protection()==VhdlDocGen::PACKBODYCLASS) |
|
465 { |
|
466 QCString temp=className;//.stripPrefix("_"); |
|
467 temp.stripPrefix("_"); |
|
468 md=VhdlDocGen::findMember(temp,memberName); |
|
469 } |
|
470 |
|
471 if (md && md->isLinkable()) // is it a linkable class |
|
472 { |
|
473 writeMultiLineCodeLink(ol,md->getReference(), |
|
474 md->getOutputFileBase(), |
|
475 md->anchor(), |
|
476 memberName, |
|
477 md->briefDescriptionAsTooltip()); |
|
478 addToSearchIndex(memberName); |
|
479 return; |
|
480 } |
|
481 // nothing found, just write out the word |
|
482 ol.linkableSymbol(g_yyLineNr,memberName,0,g_currentMemberDef?g_currentMemberDef:g_currentDefinition); |
|
483 codifyLines(memberName.data()); |
|
484 addToSearchIndex(memberName); |
|
485 }// generateMemLink |
|
486 |
|
487 |
|
488 static void generateClassOrGlobalLink(CodeOutputInterface &ol,const char *clName, bool /*typeOnly*/) |
|
489 { |
|
490 QCString className=clName; |
|
491 |
|
492 if (className.isEmpty()) return; |
|
493 |
|
494 ClassDef *cd=0; |
|
495 //MemberDef *md=0; |
|
496 //bool isLocal=FALSE; |
|
497 className.stripPrefix("_"); |
|
498 cd = getClass(className.data()); |
|
499 while (cd) |
|
500 { |
|
501 //className.stripPrefix("_"); |
|
502 QCString temp(clName); |
|
503 temp.stripPrefix("_"); |
|
504 if (cd && cd->isLinkable()) // is it a linkable class |
|
505 { |
|
506 //if ((VhdlDocGen::VhdlClasses)cd->protection()==VhdlDocGen::ARCHITECTURECLASS) |
|
507 //{ |
|
508 // temp=VhdlDocGen::getClassName(cd); |
|
509 //} |
|
510 ol.linkableSymbol(g_yyLineNr,temp,cd, |
|
511 g_currentMemberDef ? |
|
512 g_currentMemberDef : |
|
513 g_currentDefinition); |
|
514 writeMultiLineCodeLink(ol,cd->getReference(), |
|
515 cd->getOutputFileBase(), |
|
516 0, |
|
517 temp, |
|
518 cd->briefDescriptionAsTooltip()); |
|
519 addToSearchIndex(className); |
|
520 return; |
|
521 } |
|
522 Definition *d = cd->getOuterScope(); |
|
523 if (d && d->definitionType()==Definition::TypeClass) |
|
524 { |
|
525 cd = (ClassDef*)d; |
|
526 } |
|
527 else |
|
528 { |
|
529 cd = 0; |
|
530 } |
|
531 } |
|
532 |
|
533 // nothing found, just write out the word |
|
534 ol.linkableSymbol(g_yyLineNr,clName,0,g_currentMemberDef?g_currentMemberDef:g_currentDefinition); |
|
535 codifyLines(clName); |
|
536 addToSearchIndex(clName); |
|
537 }// generateClasss or global link |
|
538 |
|
539 |
|
540 /*! counts the number of lines in the input */ |
|
541 static int countLines() |
|
542 { |
|
543 const char *p=g_inputString; |
|
544 char c; |
|
545 int count=1; |
|
546 while ((c=*p)) |
|
547 { |
|
548 p++ ; |
|
549 if (c=='\n') count++; |
|
550 } |
|
551 if (p>g_inputString && *(p-1)!='\n') |
|
552 { // last line does not end with a \n, so we add an extra |
|
553 // line and explicitly terminate the line after parsing. |
|
554 count++, |
|
555 g_needsTermination=TRUE; |
|
556 } |
|
557 return count; |
|
558 } |
|
559 |
|
560 static void endFontClass() |
|
561 { |
|
562 if (g_currentFontClass) |
|
563 { |
|
564 g_code->endFontClass(); |
|
565 g_currentFontClass=0; |
|
566 } |
|
567 } |
|
568 |
|
569 static void startFontClass(const char *s) |
|
570 { |
|
571 if (s==0) return; |
|
572 endFontClass(); |
|
573 g_code->startFontClass(s); |
|
574 g_currentFontClass=s; |
|
575 } |
|
576 |
|
577 static void writeFont(const char *s,const char* text) |
|
578 { |
|
579 if (s==0 || text==0) return; |
|
580 //printf("writeFont(%d,\"%s\")\n",g_yyLineNr,text); |
|
581 g_code->startFontClass(s); |
|
582 g_code->codify(text); |
|
583 g_code->endFontClass(); |
|
584 } |
|
585 |
|
586 //---------------------------------------------------------------------------- |
|
587 |
|
588 static void appStringLower(QCString& qcs,const char* text) |
|
589 { |
|
590 qcs.resize(0); |
|
591 qcs.append(text); |
|
592 //qcs=qcs.lower(); |
|
593 qcs=qcs.stripWhiteSpace(); |
|
594 } |
|
595 |
|
596 //static void appString(QCString& qcs,const char* text) |
|
597 //{ |
|
598 // qcs.resize(0); |
|
599 // qcs.append(text); |
|
600 //} |
|
601 |
|
602 static QCString g_temp; |
|
603 |
|
604 /* writes and links a port map statement */ |
|
605 static void codifyMapLines(char *text) |
|
606 { |
|
607 if (text==0) return; |
|
608 g_temp.resize(0); |
|
609 //bool dot=FALSE; |
|
610 int wordCounter=0; |
|
611 QCString ctemp; |
|
612 //printf("codifyLines(%d,\"%s\")\n",g_yyLineNr,text); |
|
613 char *p=text,*sp=p; |
|
614 char c; |
|
615 bool done=FALSE; |
|
616 while (!done) |
|
617 { |
|
618 sp=p; |
|
619 while ((c=*p++) && c!='\n' && c!=':' && c != ' ' && c != '(' && c!='\0' && c!='\t') |
|
620 { |
|
621 if (c!=0x9) |
|
622 g_temp+=c; |
|
623 } |
|
624 if (c=='\0') return; |
|
625 if (!g_temp.isEmpty()) wordCounter++; |
|
626 |
|
627 if (!g_temp.isEmpty()) |
|
628 { |
|
629 // different kinds of component instantiations |
|
630 // xxx:yyy (generic/port) map( |
|
631 // xxx:(entity/component/configuration) yyy (generic/port) map( |
|
632 // xxx: entity yyy(zzz) (generic/port) map( |
|
633 if (wordCounter==2 || wordCounter==3) |
|
634 { |
|
635 QCString q=g_temp.lower(); // consider (upper/lower) cases |
|
636 if (q=="entity" || q=="component" || q=="configuration" || q=="port" || q=="generic") |
|
637 { |
|
638 generateMemLink(*g_code,g_CurrClass,g_temp); |
|
639 } |
|
640 else |
|
641 { |
|
642 g_PortMapComp=g_temp; |
|
643 generateClassOrGlobalLink(*g_code,g_temp); |
|
644 } |
|
645 } |
|
646 else |
|
647 { |
|
648 generateMemLink(*g_code,g_CurrClass,g_temp); |
|
649 } |
|
650 } |
|
651 ctemp.fill(c,1); |
|
652 codifyLines(ctemp.data()); |
|
653 ctemp.resize(0); |
|
654 g_temp.resize(0); |
|
655 }//while |
|
656 }//codifymaplines |
|
657 |
|
658 /* |
|
659 * writes a function|procedure prototype and links the function|procedure name |
|
660 */ |
|
661 |
|
662 static void writeFuncProto() |
|
663 { |
|
664 QList<Argument> ql; |
|
665 QCString name,ret; |
|
666 VhdlDocGen::parseFuncProto(g_FuncProto,ql,name,ret,FALSE); |
|
667 |
|
668 if (name.isEmpty()) |
|
669 { |
|
670 codifyLines(g_FuncProto.data(),g_CurrClass.data()); |
|
671 return; |
|
672 } |
|
673 QStringList qlist=QStringList::split(name,g_FuncProto,FALSE); |
|
674 QCString temp=(QCString)qlist[0]; |
|
675 codifyLines(temp.data(),g_CurrClass.data()); |
|
676 g_FuncProto.stripPrefix(temp.data()); |
|
677 temp.resize(0); |
|
678 temp=g_CurrClass; |
|
679 if (isPackageBody) |
|
680 { |
|
681 temp.stripPrefix("_");// _{package body name} |
|
682 } |
|
683 MemberDef *mdef=VhdlDocGen::findFunction(ql,name,temp,FALSE); |
|
684 |
|
685 if (mdef) |
|
686 { |
|
687 generateFuncLink(*g_code,mdef); |
|
688 g_FuncProto.stripPrefix(name.data()); |
|
689 codifyLines(g_FuncProto.data(),g_CurrClass.data()); |
|
690 } |
|
691 else |
|
692 { |
|
693 codifyLines(g_FuncProto.data(),g_CurrClass.data()); |
|
694 } |
|
695 }// writeFuncProto |
|
696 |
|
697 /* writes a process prototype to the ouput */ |
|
698 |
|
699 static void writeProcessProto(){ |
|
700 codifyLines(g_FuncProto.data(),g_CurrClass.data()); |
|
701 g_vhdlKeyDict.clear(); |
|
702 }// writeProcessProto |
|
703 |
|
704 /* writes a keyword */ |
|
705 |
|
706 static bool writeColoredWord(QCString& word ) |
|
707 { |
|
708 QCString qcs=word.lower(); |
|
709 QCString *ss=VhdlDocGen::findKeyWord(qcs); |
|
710 if (ss) |
|
711 { |
|
712 writeFont(ss->data(),word.data()); |
|
713 return TRUE; |
|
714 } |
|
715 return FALSE; |
|
716 } |
|
717 |
|
718 #undef YY_INPUT |
|
719 #define YY_INPUT(buf,result,max_size) result=yyread(buf,max_size); |
|
720 |
|
721 static int yyread(char *buf,int max_size) |
|
722 { |
|
723 int c=0; |
|
724 while( c < max_size && g_inputString[g_inputPosition] ) |
|
725 { |
|
726 *buf = g_inputString[g_inputPosition++] ; |
|
727 c++; buf++; |
|
728 } |
|
729 return c; |
|
730 } |
|
731 |
|
732 %} |
|
733 |
|
734 |
|
735 B [ \t] |
|
736 BN [ \t\n\r] |
|
737 STRING ["][^"\n]*["] |
|
738 NAME [a-z_A-Z][ a-z_A-Z0-9]* |
|
739 FUNCNAME [a-z_A-Z"][a-z_A-Z0-9+*"/=<>-]* |
|
740 ID "$"?[a-z_A-Z][a-z_A-Z0-9]* |
|
741 SPECSIGN [:;, +*&\/=<>'\t]* |
|
742 DIGITSS [0-9]+|[0-9]+("#")*[0-9_a-fA-F\+\.\-]+("#")* |
|
743 ALLTYPESMAP {B}*[_a-zA-Z0-9. ]+{BN}* |
|
744 ALLTYPESMAP1 {BN}*[_a-zA-Z0-9.() ]+{BN}* |
|
745 |
|
746 ARCHITECTURE ^{B}*("architecture"){BN}+{FUNCNAME}{BN}+("of"){BN}+{FUNCNAME} |
|
747 PROCESS ({BN}*{FUNCNAME}{BN}*[:]+{BN}*("process"){BN}*[(]*)|[^a-zA-Z]("process "|"process("){BN}*[ (]*|[^a-zA-Z]("process"){BN}+ |
|
748 |
|
749 END1 {B}*("end "){BN}+("if"|"case"|"loop"|"generate"|"for") |
|
750 END2 [^a-zA-Z_]("end"){BN}*[;] |
|
751 END3 {BN}*[^a-zA-Z]("end"){BN}+{FUNCNAME}{BN}*[;] |
|
752 END4 {B}*("end"){BN}+"function"{BN}+{FUNCNAME}{BN}*[;] |
|
753 ENDEFUNC {END3}|{END4}|{END2} |
|
754 |
|
755 KEYWORD ("new"|"event"|"break"|"case"|"end"|"loop"|"else"|"for"|"goto"|"if"|"return"|"generate"|"is"|"while"|"in") |
|
756 TYPEKW ^{B}*("type"|"subtype"|"constant"|"attribute"|"signal"|"variable","alias","configuration") |
|
757 FUNC ^{B}*("function"|"procedure"){BN}*{FUNCNAME}{BN}*("(") |
|
758 |
|
759 ARITHOP "+"|"-"|"/"|"*"|"%"|"/="|":=" |
|
760 ASSIGNOP "="|"*="|"/="|"%="|"+="|"-="|"<<="|">>="|"&="|"^="|"|=" |
|
761 LOGICOP "=="|"!="|">"|"<"|">="|"<="|"&&"|"||"|"!" |
|
762 BITOP "&"|"|"|"^"|"<<"|">>"|"~" |
|
763 OPERATOR {ARITHOP}|{ASSIGNOP}|{LOGICOP}|{BITOP} |
|
764 |
|
765 PORT {B}*("port"){BN}*("(") |
|
766 GENERIC {B}*("generic"){BN}*("(") |
|
767 |
|
768 BRACEOPEN [(]{1} |
|
769 BRACECLOSE [)]{1} |
|
770 |
|
771 TEXTT {B}*"--"[^\n]* |
|
772 |
|
773 MAPCOMPONENT1 ({ALLTYPESMAP}[:]{ALLTYPESMAP}{TEXTT}*{BN}+("port"|"generic"){BN}+("map"){BN}*("("){1}) |
|
774 MAPCOMPONENT2 {BN}*("port"|"generic"){BN}+("map"){BN}*("("){1} |
|
775 MAPCOMPONENT3 ({ALLTYPESMAP}[:]{BN}*{ALLTYPESMAP1}{TEXTT}*{BN}+("port"|"generic"){BN}+("map"){BN}*("("){1}) |
|
776 MAPCOMPONENT4 ({ALLTYPESMAP}[:]{BN}*("entity"|"component"|"configuration"){BN}+{ALLTYPESMAP1}{TEXTT}*{BN}*("port"|"generic"){BN}*("map"){BN}*("("){1}) |
|
777 |
|
778 %option noyywrap |
|
779 %option nounput |
|
780 |
|
781 %x Bases |
|
782 %x ParseType |
|
783 %x ParseFuncProto |
|
784 %x ParseComponent |
|
785 %x ParsePackage |
|
786 %x ParseProcessProto |
|
787 %x ClassName |
|
788 %x PackageName |
|
789 %x ClassVar |
|
790 %x ClassesName |
|
791 %x Map |
|
792 %x Body |
|
793 |
|
794 %% |
|
795 |
|
796 . { |
|
797 BEGIN(Bases); |
|
798 } |
|
799 |
|
800 <Map>{BRACEOPEN} { |
|
801 g_braceCount++; |
|
802 writeFont("vhdlchar",vhdlcodeYYtext); |
|
803 BEGIN(Map); |
|
804 } |
|
805 |
|
806 <Map>[^()\n,--]* { /* write and link a port map lines */ |
|
807 QCString tt(vhdlcodeYYtext); |
|
808 VhdlDocGen::deleteAllChars(tt,','); |
|
809 QRegExp r("=>"); |
|
810 QStringList ql=QStringList::split(r,tt,FALSE); |
|
811 if (ql.count()>=2) |
|
812 { |
|
813 unsigned int index=0; |
|
814 QCString t1=(QCString)ql[0]; |
|
815 char cc=t1.at(index); |
|
816 while (cc==' ' || cc=='\t') |
|
817 { |
|
818 char c2[2]; |
|
819 c2[0]=cc; |
|
820 c2[1]=0; |
|
821 g_code->codify(c2); |
|
822 index++; |
|
823 if (index>=t1.size()) break; |
|
824 cc=t1.at(index); |
|
825 } |
|
826 |
|
827 QCString s1=(QCString)ql[0]; |
|
828 s1=s1.stripWhiteSpace(); |
|
829 |
|
830 // if (!g_PortMapComp.isEmpty()) |
|
831 generateMemLink(*g_code,g_PortMapComp,s1); |
|
832 while (index++<t1.size()) |
|
833 { |
|
834 char cc=t1.at(index); |
|
835 if (cc==' ' || cc=='\t') |
|
836 { |
|
837 char c2[2]; |
|
838 c2[0]=cc; |
|
839 c2[1]=0; |
|
840 g_code->codify(c2); |
|
841 } |
|
842 } |
|
843 codifyLines("=>"); |
|
844 index=0; |
|
845 QCString s2=(QCString)ql[1]; |
|
846 t1=s2; |
|
847 cc=t1.at(index); |
|
848 while (cc==' ' || cc=='\t') |
|
849 { |
|
850 char c2[2]; |
|
851 c2[0]=cc; |
|
852 c2[1]=0; |
|
853 g_code->codify(c2); |
|
854 index++; |
|
855 if (index>=t1.size()) break; |
|
856 cc=t1.at(index); |
|
857 } |
|
858 s2=s2.stripWhiteSpace(); |
|
859 if (!checkString(s2)) |
|
860 generateMemLink(*g_code,g_CurrClass,s2); |
|
861 while (index++<t1.size()) |
|
862 { |
|
863 if (t1.at(index)==' ') |
|
864 { |
|
865 g_code->codify(" "); |
|
866 } |
|
867 } |
|
868 } |
|
869 else |
|
870 { |
|
871 codifyLines(vhdlcodeYYtext,g_CurrClass.data()); |
|
872 } |
|
873 BEGIN(Map); |
|
874 } |
|
875 |
|
876 <Map>"\n"|"," { |
|
877 codifyLines(vhdlcodeYYtext); |
|
878 BEGIN(Map); |
|
879 } |
|
880 |
|
881 <Map>{BRACECLOSE} { |
|
882 g_braceCount--; |
|
883 writeFont("vhdlchar",vhdlcodeYYtext); |
|
884 if (g_braceCount==0) |
|
885 { |
|
886 BEGIN(Bases); |
|
887 } |
|
888 } |
|
889 |
|
890 <ParseFuncProto>{NAME} { |
|
891 QCString tmp(vhdlcodeYYtext); |
|
892 tmp=tmp.stripWhiteSpace(); |
|
893 appStringLower(g_PrevString,vhdlcodeYYtext); |
|
894 g_vhdlKeyDict.insert(g_PrevString,new QCString(g_PrevString.data())); |
|
895 if (!writeColoredWord(tmp)) |
|
896 { |
|
897 generateMemLink(*g_code,g_CurrClass,tmp); |
|
898 } |
|
899 BEGIN(Bases); |
|
900 } |
|
901 |
|
902 <ParseType>{STRING} { |
|
903 QCString qcs(vhdlcodeYYtext); |
|
904 VhdlDocGen::deleteAllChars(qcs,'"'); |
|
905 VhdlDocGen::deleteAllChars(qcs,' '); |
|
906 if (VhdlDocGen::isNumber(qcs)) |
|
907 writeFont("vhdllogic",vhdlcodeYYtext); |
|
908 else |
|
909 writeFont("keyword",vhdlcodeYYtext); |
|
910 } |
|
911 |
|
912 <ParseType>"\n" { |
|
913 g_FuncProto.append(vhdlcodeYYtext); |
|
914 if (isProto) |
|
915 { |
|
916 codifyLines(vhdlcodeYYtext); |
|
917 } |
|
918 BEGIN(ParseType); |
|
919 } |
|
920 |
|
921 |
|
922 <ParseType>{TEXTT} { |
|
923 g_FuncProto.append(vhdlcodeYYtext); |
|
924 if (isProto) |
|
925 { |
|
926 writeFont("keyword",vhdlcodeYYtext); |
|
927 } |
|
928 BEGIN(ParseType); |
|
929 } |
|
930 |
|
931 <ParseType>{ENDEFUNC} { |
|
932 QRegExp regg("[\\s]"); |
|
933 QCString tt(vhdlcodeYYtext); |
|
934 codifyLines(vhdlcodeYYtext,g_CurrClass.data()); |
|
935 tt=tt.lower(); |
|
936 VhdlDocGen::deleteAllChars(tt,';'); |
|
937 tt.stripWhiteSpace(); |
|
938 QStringList ql=QStringList::split(regg,tt,FALSE); |
|
939 int index=ql.findIndex(QCString("if"))+1; |
|
940 index+=ql.findIndex(QCString("case"))+1; |
|
941 index+=ql.findIndex(QCString("loop"))+1; |
|
942 index+=ql.findIndex(QCString("generate"))+1; |
|
943 if (index==0) |
|
944 { |
|
945 BEGIN(Bases); |
|
946 } |
|
947 else |
|
948 { |
|
949 BEGIN(ParseType); |
|
950 } |
|
951 } |
|
952 |
|
953 <ParseType>{END1} { |
|
954 codifyLines(vhdlcodeYYtext,g_CurrClass.data()); |
|
955 g_vhdlKeyDict.clear(); |
|
956 } |
|
957 |
|
958 <ParseType>^{B}*("begin "|"begin") { |
|
959 codifyLines(vhdlcodeYYtext,g_CurrClass.data()); |
|
960 isFuncProto=FALSE; |
|
961 } |
|
962 |
|
963 <ParseType>{SPECSIGN} { |
|
964 g_FuncProto.append(vhdlcodeYYtext); |
|
965 if (isProto) |
|
966 { |
|
967 codifyLines(vhdlcodeYYtext,g_CurrClass.data()); |
|
968 } |
|
969 } |
|
970 |
|
971 <ParseType>["_a-zA-Z0-9]* { |
|
972 QCString val(vhdlcodeYYtext); |
|
973 g_FuncProto.append(vhdlcodeYYtext); |
|
974 appStringLower(g_PrevString,vhdlcodeYYtext); |
|
975 |
|
976 if (isFuncProto && g_braceCount==0) |
|
977 { |
|
978 g_vhdlKeyDict.insert(g_PrevString,new QCString(g_PrevString.data())); |
|
979 } |
|
980 |
|
981 if (isProto) |
|
982 { |
|
983 if (!writeColoredWord(val)) |
|
984 { |
|
985 if (!isFuncProto && !g_vhdlKeyDict.find(g_PrevString)) |
|
986 { |
|
987 val=val.stripWhiteSpace(); |
|
988 if (VhdlDocGen::isNumber(val)) |
|
989 { |
|
990 startFontClass("vhdllogic"); |
|
991 codifyLines(vhdlcodeYYtext,g_CurrClass.data()); |
|
992 endFontClass(); |
|
993 } |
|
994 else |
|
995 generateMemLink(*g_code,g_CurrClass,val); |
|
996 } |
|
997 else |
|
998 { |
|
999 codifyLines(vhdlcodeYYtext,g_CurrClass.data()); |
|
1000 } |
|
1001 } |
|
1002 } |
|
1003 BEGIN(ParseType); |
|
1004 } |
|
1005 |
|
1006 <ParseType>{BRACEOPEN} { |
|
1007 g_braceCount++; |
|
1008 g_FuncProto+='('; |
|
1009 if (isProto) |
|
1010 { |
|
1011 writeFont("vhdlchar",vhdlcodeYYtext); |
|
1012 } |
|
1013 BEGIN(ParseType); |
|
1014 } |
|
1015 |
|
1016 <ParseType>{BRACECLOSE} { |
|
1017 g_braceCount--; |
|
1018 g_FuncProto+=')'; |
|
1019 if (isProto) |
|
1020 { |
|
1021 writeFont("vhdlchar",vhdlcodeYYtext); |
|
1022 } |
|
1023 if (g_braceCount==0 && !isProto)// && !isPackageBody) |
|
1024 { |
|
1025 isProto=TRUE; |
|
1026 appStringLower(g_PrevString,vhdlcodeYYtext); |
|
1027 writeFuncProto(); |
|
1028 BEGIN(Bases); |
|
1029 } |
|
1030 if (isPackageBody) |
|
1031 { |
|
1032 BEGIN(ParseType); |
|
1033 } |
|
1034 } |
|
1035 |
|
1036 |
|
1037 <ClassesName>{FUNCNAME} { |
|
1038 QDict<QCString> mem; |
|
1039 appStringLower(g_PrevString,vhdlcodeYYtext); |
|
1040 g_CurrClass.resize(0); |
|
1041 g_CurrClass.append(vhdlcodeYYtext); |
|
1042 g_CurrClass=g_CurrClass.stripWhiteSpace(); |
|
1043 |
|
1044 if (!writeColoredWord(g_CurrScope)) |
|
1045 { |
|
1046 generateClassOrGlobalLink(*g_code,vhdlcodeYYtext); |
|
1047 } |
|
1048 else |
|
1049 { |
|
1050 codifyLines(vhdlcodeYYtext,g_CurrClass.data()); |
|
1051 } |
|
1052 BEGIN(Bases); |
|
1053 } |
|
1054 |
|
1055 |
|
1056 <ParseComponent>{BRACEOPEN} { |
|
1057 g_braceCount++; |
|
1058 g_code->codify(vhdlcodeYYtext); |
|
1059 } |
|
1060 |
|
1061 |
|
1062 <ParseComponent>{BRACECLOSE} { |
|
1063 g_braceCount--; |
|
1064 g_code->codify(vhdlcodeYYtext); |
|
1065 if (g_braceCount==0 && !isComponent) |
|
1066 { |
|
1067 g_tempComp.resize(0); |
|
1068 BEGIN(Bases); |
|
1069 } |
|
1070 else |
|
1071 { |
|
1072 BEGIN(ParseComponent); |
|
1073 } |
|
1074 } |
|
1075 |
|
1076 <ParseComponent>{B}*"-" { |
|
1077 if (strlen(vhdlcodeYYtext)>=2) // found text ? |
|
1078 { |
|
1079 writeFont("keyword",vhdlcodeYYtext); |
|
1080 } |
|
1081 else |
|
1082 { |
|
1083 writeFont("vhdlchar",vhdlcodeYYtext); |
|
1084 } |
|
1085 } |
|
1086 |
|
1087 <ParseComponent>{SPECSIGN} { |
|
1088 codifyLines(vhdlcodeYYtext); |
|
1089 } |
|
1090 |
|
1091 |
|
1092 |
|
1093 <ParseComponent>"\n"|" " { |
|
1094 codifyLines(vhdlcodeYYtext); |
|
1095 } |
|
1096 |
|
1097 <ParseComponent>{DIGITSS} { |
|
1098 startFontClass("vhdllogic"); |
|
1099 codifyLines(vhdlcodeYYtext); |
|
1100 endFontClass(); |
|
1101 } |
|
1102 |
|
1103 <ParseComponent>{PORT} { |
|
1104 codifyLines(vhdlcodeYYtext); |
|
1105 g_braceCount=1; |
|
1106 isComponent=FALSE; |
|
1107 } |
|
1108 |
|
1109 <ParseComponent>{GENERIC} { |
|
1110 codifyLines(vhdlcodeYYtext); |
|
1111 g_braceCount=1; |
|
1112 } |
|
1113 |
|
1114 <ParseComponent>[_a-zA_Z][_a-zA-Z0-9]* { |
|
1115 QCString temp(vhdlcodeYYtext); |
|
1116 appStringLower(g_PrevString,vhdlcodeYYtext); |
|
1117 if (!checkString(temp)){ |
|
1118 if (!writeColoredWord(g_PrevString)) |
|
1119 { |
|
1120 generateMemLink(*g_code,g_tempComp,temp); |
|
1121 } |
|
1122 } |
|
1123 } |
|
1124 |
|
1125 <ParseComponent>{STRING} { |
|
1126 QCString temp(vhdlcodeYYtext); |
|
1127 if (!checkString(temp)) |
|
1128 codifyLines(vhdlcodeYYtext); |
|
1129 } |
|
1130 |
|
1131 |
|
1132 <ParseProcessProto>[^()]* { |
|
1133 g_FuncProto.append(vhdlcodeYYtext); |
|
1134 } |
|
1135 |
|
1136 |
|
1137 |
|
1138 <ParseProcessProto>{BRACEOPEN} { |
|
1139 g_FuncProto.append(vhdlcodeYYtext); |
|
1140 g_braceCount++; |
|
1141 } |
|
1142 |
|
1143 <ParseProcessProto>{BRACECLOSE} { |
|
1144 g_FuncProto.append(vhdlcodeYYtext); |
|
1145 g_braceCount--; |
|
1146 if (g_braceCount==0) |
|
1147 { |
|
1148 writeProcessProto(); |
|
1149 BEGIN(Bases); |
|
1150 } |
|
1151 } |
|
1152 |
|
1153 <ParsePackage>[^:;]* { //found package |
|
1154 QCString temp(vhdlcodeYYtext); |
|
1155 QStringList strl=QStringList::split(".",temp,FALSE); |
|
1156 |
|
1157 if (strl.count()>2) |
|
1158 { |
|
1159 QCString s1=(QCString)strl[0]; |
|
1160 QCString s2=(QCString)strl[1]; |
|
1161 QCString s3=(QCString)strl[2]; |
|
1162 s1.append("."); |
|
1163 s3.prepend("."); |
|
1164 codifyLines(s1.data(),g_CurrClass.data()); |
|
1165 ClassDef *cd=VhdlDocGen::getPackageName(s2); |
|
1166 if (cd) |
|
1167 { |
|
1168 generateClassOrGlobalLink(*g_code,s2.data()); |
|
1169 } |
|
1170 else |
|
1171 { |
|
1172 codifyLines(s2.data()); |
|
1173 } |
|
1174 codifyLines(s3.data()); |
|
1175 } |
|
1176 else |
|
1177 { |
|
1178 writeFont("keywordflow",vhdlcodeYYtext); |
|
1179 } |
|
1180 BEGIN(Bases); |
|
1181 } |
|
1182 |
|
1183 <Bases>{MAPCOMPONENT1}|{MAPCOMPONENT2}|{MAPCOMPONENT3}|{MAPCOMPONENT4} { // found port or generic map |
|
1184 QCString tt(vhdlcodeYYtext); |
|
1185 /* |
|
1186 if (tt.contains(':',FALSE)) |
|
1187 { |
|
1188 isStartMap=TRUE; |
|
1189 } |
|
1190 else |
|
1191 { |
|
1192 isStartMap=FALSE; |
|
1193 } |
|
1194 */ |
|
1195 int j=tt.find('.'); |
|
1196 |
|
1197 if (j>0) |
|
1198 { |
|
1199 QCString left=tt.left(j+1); |
|
1200 codifyLines(left.data()); |
|
1201 tt=tt.right(tt.length()-j-1); |
|
1202 left=VhdlDocGen::getIndexWord(tt.data(),0); |
|
1203 if (!left.isEmpty()) |
|
1204 { |
|
1205 if (left.contains('(')) |
|
1206 { |
|
1207 j=left.find('(',FALSE); |
|
1208 QCString name=left.left(j); |
|
1209 generateClassOrGlobalLink(*g_code,name.data()); |
|
1210 g_PortMapComp=name; |
|
1211 name=tt.right(tt.length()-name.length()); |
|
1212 codifyLines(name.data()); |
|
1213 } |
|
1214 else |
|
1215 { |
|
1216 generateClassOrGlobalLink(*g_code,left.data()); |
|
1217 tt=tt.right(tt.length()-left.length()-1); |
|
1218 tt.prepend(" "); |
|
1219 g_PortMapComp=left; |
|
1220 codifyLines(tt.data()); |
|
1221 } |
|
1222 } |
|
1223 } |
|
1224 else |
|
1225 { |
|
1226 if (tt.contains(':',FALSE)) |
|
1227 codifyMapLines(tt.data()); |
|
1228 else |
|
1229 codifyLines(tt.data()); |
|
1230 } |
|
1231 g_braceCount=1; |
|
1232 BEGIN(Map); |
|
1233 } |
|
1234 |
|
1235 <Bases>^{B}*("component"){BN}+{FUNCNAME} { // found component |
|
1236 appStringLower(g_PrevString,vhdlcodeYYtext); |
|
1237 // writeFont("keywordflow",VhdlDocGen::getIndexWord(vhdlcodeYYtext,0).data()); |
|
1238 // writeFont("vhdlkeyword"," "); |
|
1239 QCString temp=VhdlDocGen::getIndexWord(vhdlcodeYYtext,1); |
|
1240 temp=temp.stripWhiteSpace(); |
|
1241 VhdlDocGen::deleteAllChars(temp,'\n'); |
|
1242 g_tempComp=temp; |
|
1243 codifyLines(vhdlcodeYYtext,temp.data(),TRUE); |
|
1244 g_braceCount=0; |
|
1245 |
|
1246 //if (getClass(temp.data())) |
|
1247 // generateClassOrGlobalLink(*g_code,temp.data()); |
|
1248 //else |
|
1249 // generateMemLink(*g_code,g_CurrClass,temp); |
|
1250 |
|
1251 isComponent=TRUE; |
|
1252 BEGIN(ParseComponent); |
|
1253 } |
|
1254 |
|
1255 |
|
1256 |
|
1257 <Bases>{ARCHITECTURE} { // found architecture |
|
1258 g_PortMapComp.resize(0); |
|
1259 // writeFont("vhdlkeyword",VhdlDocGen::getIndexWord(vhdlcodeYYtext,0).data()); |
|
1260 // writeFont("vhdlkeyword"," "); |
|
1261 // writeFont("vhdlchar",VhdlDocGen::getIndexWord(vhdlcodeYYtext,1).data()); |
|
1262 // writeFont("vhdlkeyword"," "); |
|
1263 // writeFont("vhdlkeyword",VhdlDocGen::getIndexWord(vhdlcodeYYtext,2).data()); |
|
1264 // writeFont("vhdlkeyword"," "); |
|
1265 //QCString temp=VhdlDocGen::getIndexWord(vhdlcodeYYtext,1); |
|
1266 //temp=temp.stripWhiteSpace(); |
|
1267 //temp+=("-"); |
|
1268 //temp+=VhdlDocGen::getIndexWord(vhdlcodeYYtext,3); |
|
1269 QCString temp = VhdlDocGen::getIndexWord(vhdlcodeYYtext,3); |
|
1270 temp+="::"; |
|
1271 temp+=VhdlDocGen::getIndexWord(vhdlcodeYYtext,1); |
|
1272 g_CurrClass=temp; |
|
1273 VhdlDocGen::deleteAllChars(temp,'\n'); |
|
1274 codifyLines(vhdlcodeYYtext,temp.data(),TRUE); |
|
1275 //generateClassOrGlobalLink(*g_code,temp.data()); |
|
1276 isPackageBody=FALSE; |
|
1277 BEGIN(ClassName); |
|
1278 } |
|
1279 |
|
1280 |
|
1281 <Bases>^{B}*("package "){BN}*("body"){BN}*{FUNCNAME} { // found package body |
|
1282 QCString ss(vhdlcodeYYtext); |
|
1283 QCString temp=VhdlDocGen::getIndexWord(vhdlcodeYYtext,2); |
|
1284 QStringList ql=QStringList::split(temp,ss,FALSE); |
|
1285 QCString ll=(QCString)ql[0]; |
|
1286 codifyLines(ll.data(),g_CurrClass.data()); |
|
1287 temp=temp.stripWhiteSpace(); |
|
1288 temp.prepend("_"); |
|
1289 generateClassOrGlobalLink(*g_code,temp.data()); |
|
1290 g_CurrClass.resize(0); |
|
1291 g_CurrClass=temp; |
|
1292 isProto=FALSE; |
|
1293 isPackageBody=TRUE; |
|
1294 // BEGIN(ClassesName); |
|
1295 } |
|
1296 |
|
1297 <Bases>{PROCESS} { // found process |
|
1298 isFuncProto=TRUE; |
|
1299 g_FuncProto.resize(0); |
|
1300 g_FuncProto.append(vhdlcodeYYtext); |
|
1301 g_vhdlKeyDict.clear(); |
|
1302 appStringLower(g_PrevString,vhdlcodeYYtext); |
|
1303 if (g_PrevString.contains('(')) |
|
1304 { |
|
1305 g_braceCount=1; |
|
1306 BEGIN(ParseProcessProto); |
|
1307 } |
|
1308 else |
|
1309 { |
|
1310 writeProcessProto(); |
|
1311 } |
|
1312 } |
|
1313 |
|
1314 <Bases>("end"){BN}+("process") { // end of process |
|
1315 isFuncProto=FALSE; |
|
1316 codifyLines(vhdlcodeYYtext); |
|
1317 BEGIN(Bases); |
|
1318 } |
|
1319 |
|
1320 |
|
1321 <Bases>^{B}*("begin "|"begin") { |
|
1322 isFuncProto=FALSE; |
|
1323 writeFont("vhdlkeyword",vhdlcodeYYtext); |
|
1324 } |
|
1325 |
|
1326 <Bases>^{B}*("use"|"library"){BN}+ { //found package or library |
|
1327 writeFont("vhdlkeyword",vhdlcodeYYtext); |
|
1328 BEGIN(ParsePackage); |
|
1329 } |
|
1330 |
|
1331 |
|
1332 <Bases>^{B}*("use"){BN}+("configuration")[^\n]* { |
|
1333 codifyLines(vhdlcodeYYtext); |
|
1334 } |
|
1335 |
|
1336 |
|
1337 |
|
1338 <Bases>{FUNC} { // found function|procedure |
|
1339 g_vhdlKeyDict.clear(); |
|
1340 g_FuncProto.resize(0); |
|
1341 isProto=FALSE; |
|
1342 g_FuncProto.append(vhdlcodeYYtext); |
|
1343 g_braceCount=1; |
|
1344 BEGIN(ParseType); |
|
1345 } |
|
1346 |
|
1347 |
|
1348 |
|
1349 <Bases>^{B}*("entity"|"package"){BN}+ { |
|
1350 appStringLower(g_PrevString,vhdlcodeYYtext); |
|
1351 writeFont("keywordflow",vhdlcodeYYtext); |
|
1352 isPackageBody=FALSE; |
|
1353 BEGIN(ClassesName); |
|
1354 } |
|
1355 |
|
1356 |
|
1357 <Bases>{KEYWORD} { // found keyword |
|
1358 QCString qcs(vhdlcodeYYtext); |
|
1359 if (!writeColoredWord(qcs)) |
|
1360 { |
|
1361 startFontClass("vhdlchar"); |
|
1362 g_code->codify(vhdlcodeYYtext); |
|
1363 endFontClass(); |
|
1364 } |
|
1365 } |
|
1366 |
|
1367 |
|
1368 <Bases>{ID} { |
|
1369 appStringLower(g_PrevString,vhdlcodeYYtext); |
|
1370 QCString temp(vhdlcodeYYtext); |
|
1371 temp=temp.stripWhiteSpace(); |
|
1372 |
|
1373 if (!writeColoredWord(temp)) |
|
1374 { |
|
1375 startFontClass("vhdlchar"); |
|
1376 generateMemLink(*g_code,g_CurrClass,temp); |
|
1377 endFontClass(); |
|
1378 } |
|
1379 } |
|
1380 |
|
1381 <Bases,ParseComponent>{DIGITSS} { |
|
1382 startFontClass("vhdllogic"); |
|
1383 codifyLines(vhdlcodeYYtext); |
|
1384 endFontClass(); |
|
1385 } |
|
1386 |
|
1387 <Bases>^{B}*("use"){BN}+("entity"|"component")[^\n]* { |
|
1388 codifyLines(vhdlcodeYYtext,g_CurrClass.data(),TRUE); |
|
1389 } |
|
1390 |
|
1391 |
|
1392 <Bases>{TYPEKW} { |
|
1393 codifyLines(vhdlcodeYYtext); |
|
1394 if (isFuncProto) |
|
1395 { |
|
1396 BEGIN(ParseFuncProto); |
|
1397 } |
|
1398 else |
|
1399 { |
|
1400 BEGIN(Bases); |
|
1401 } |
|
1402 } |
|
1403 |
|
1404 <Bases>{OPERATOR} { |
|
1405 startFontClass("vhdlchar"); |
|
1406 g_code->codify(vhdlcodeYYtext); |
|
1407 endFontClass(); |
|
1408 } |
|
1409 |
|
1410 <Bases>","|"."|":"|"'"|"("|")" { |
|
1411 startFontClass("vhdlchar"); |
|
1412 g_code->codify(vhdlcodeYYtext); |
|
1413 endFontClass(); |
|
1414 } |
|
1415 |
|
1416 <Bases>{STRING} { |
|
1417 QCString qcs(vhdlcodeYYtext); |
|
1418 VhdlDocGen::deleteAllChars(qcs,'"'); |
|
1419 VhdlDocGen::deleteAllChars(qcs,' '); |
|
1420 |
|
1421 if (VhdlDocGen::isNumber(qcs)) |
|
1422 writeFont("vhdllogic",vhdlcodeYYtext); |
|
1423 else |
|
1424 writeFont("keyword",vhdlcodeYYtext); |
|
1425 } |
|
1426 |
|
1427 <*>\n { |
|
1428 codifyLines(vhdlcodeYYtext); |
|
1429 BEGIN(Bases); |
|
1430 } |
|
1431 |
|
1432 <*>. { |
|
1433 g_code->codify(vhdlcodeYYtext); |
|
1434 } |
|
1435 |
|
1436 <*>\n{TEXTT} { // found normal or special comment on its own line |
|
1437 QCString text(vhdlcodeYYtext); |
|
1438 int i=text.find("--"); |
|
1439 if (text.mid(i,3)=="--!" && // hide special comment |
|
1440 Config_getBool("STRIP_CODE_COMMENTS")) |
|
1441 { |
|
1442 g_yyLineNr++; // skip complete line |
|
1443 } |
|
1444 else // normal comment |
|
1445 { |
|
1446 startFontClass("comment"); |
|
1447 codifyLines(text); |
|
1448 endFontClass(); |
|
1449 } |
|
1450 } |
|
1451 <*>{TEXTT} { // found normal or special comment after something |
|
1452 QCString text(vhdlcodeYYtext); |
|
1453 int i=text.find("--"); |
|
1454 if (text.mid(i,3)=="--!" && |
|
1455 Config_getBool("STRIP_CODE_COMMENTS")) |
|
1456 { |
|
1457 // hide special comment |
|
1458 } |
|
1459 else // normal comment |
|
1460 { |
|
1461 startFontClass("comment"); |
|
1462 codifyLines(text); |
|
1463 endFontClass(); |
|
1464 } |
|
1465 } |
|
1466 |
|
1467 |
|
1468 %% |
|
1469 |
|
1470 /*@ ---------------------------------------------------------------------------- |
|
1471 */ |
|
1472 |
|
1473 void resetVhdlCodeParserState() |
|
1474 { |
|
1475 g_vhdlKeyDict.setAutoDelete(TRUE); |
|
1476 g_vhdlKeyDict.clear(); |
|
1477 } |
|
1478 |
|
1479 void parseVhdlCode(CodeOutputInterface &od,const char *className,const QCString &s, |
|
1480 bool exBlock, const char *exName,FileDef *fd, |
|
1481 int startLine,int endLine,bool inlineFragment, |
|
1482 MemberDef *memberDef) |
|
1483 { |
|
1484 //printf("***parseCode() exBlock=%d exName=%s fd=%p\n",exBlock,exName,fd); |
|
1485 if (s.isEmpty()) return; |
|
1486 if (memberDef) |
|
1487 { |
|
1488 ClassDef *dd=memberDef->getClassDef(); |
|
1489 if (dd) g_CurrClass=dd->className(); |
|
1490 startLine--; |
|
1491 } |
|
1492 resetVhdlCodeParserState(); |
|
1493 g_code = &od; |
|
1494 g_inputString = s; |
|
1495 g_inputPosition = 0; |
|
1496 g_currentFontClass = 0; |
|
1497 g_needsTermination = FALSE; |
|
1498 |
|
1499 if (endLine!=-1) |
|
1500 g_inputLines = endLine+1; |
|
1501 else |
|
1502 g_inputLines = countLines(); |
|
1503 |
|
1504 if (startLine!=-1) |
|
1505 g_yyLineNr = startLine; |
|
1506 else |
|
1507 g_yyLineNr = 1; |
|
1508 |
|
1509 |
|
1510 // g_theCallContext.clear(); |
|
1511 g_classScope = className; |
|
1512 g_exampleName = exName; |
|
1513 g_sourceFileDef = fd; |
|
1514 if (exBlock && fd==0) |
|
1515 { |
|
1516 // create a dummy filedef for the example |
|
1517 g_sourceFileDef = new FileDef("",exName); |
|
1518 } |
|
1519 if (g_sourceFileDef) |
|
1520 { |
|
1521 setCurrentDoc(g_sourceFileDef->name(),g_sourceFileDef->getSourceFileBase()); |
|
1522 } |
|
1523 g_currentDefinition = 0; |
|
1524 g_currentMemberDef = 0; |
|
1525 g_vhdlMember=0; |
|
1526 if (!g_exampleName.isEmpty()) |
|
1527 { |
|
1528 g_exampleFile = convertNameToFile(g_exampleName+"-example"); |
|
1529 } |
|
1530 g_includeCodeFragment = inlineFragment; |
|
1531 if (!memberDef) |
|
1532 { |
|
1533 startCodeLine(); |
|
1534 } |
|
1535 // g_type.resize(0); |
|
1536 // g_name.resize(0); |
|
1537 // g_args.resize(0); |
|
1538 g_parmName.resize(0); |
|
1539 g_parmType.resize(0); |
|
1540 if (memberDef) |
|
1541 { |
|
1542 setParameterList(memberDef); |
|
1543 } |
|
1544 vhdlcodeYYrestart( vhdlcodeYYin ); |
|
1545 BEGIN( Bases ); |
|
1546 vhdlcodeYYlex(); |
|
1547 g_lexInit=TRUE; |
|
1548 if (g_needsTermination) |
|
1549 { |
|
1550 endCodeLine(); |
|
1551 } |
|
1552 if (exBlock && g_sourceFileDef) |
|
1553 { |
|
1554 // delete the temporary file definition used for this example |
|
1555 delete g_sourceFileDef; |
|
1556 g_sourceFileDef=0; |
|
1557 } |
|
1558 return; |
|
1559 } |
|
1560 |
|
1561 void codeFreeVhdlScanner() |
|
1562 { |
|
1563 #if defined(YY_FLEX_SUBMINOR_VERSION) |
|
1564 if (g_lexInit) |
|
1565 { |
|
1566 vhdlcodeYYlex_destroy(); |
|
1567 } |
|
1568 #endif |
|
1569 } |
|
1570 |
|
1571 #if !defined(YY_FLEX_SUBMINOR_VERSION) |
|
1572 extern "C" { // some bogus code to keep the compiler happy |
|
1573 void vhdlcodeYYdummy() { yy_flex_realloc(0,0); } |
|
1574 } |
|
1575 #elif YY_FLEX_SUBMINOR_VERSION<33 |
|
1576 #error "You seem to be using a version of flex newer than 2.5.4 but older than 2.5.33. These versions do NOT work with doxygen! Please use version <=2.5.4 or >=2.5.33 or expect things to be parsed wrongly!" |
|
1577 #endif |
|
1578 |
|
1579 |
|
1580 |
|
1581 |