1 ///////////////////////////////////////////////////////////////////////////// 
   3 // Purpose:     Contrib. demo 
   4 // Author:      Aleksandras Gluchovas 
   8 // Copyright:   (c) Aleskandars Gluchovas 
   9 // Licence:       wxWindows licence 
  10 ///////////////////////////////////////////////////////////////////////////// 
  13 #  pragma implementation "srcparser.h" 
  16 // For compilers that support precompilation, includes "wx/wx.h". 
  17 #include "wx/wxprec.h" 
  32 #include "srcparser.h" 
  34 /***** Implementation for class spVisitor *****/ 
  36 void spVisitor::VisitAll( spContext
& atContext
, 
  40     mSiblingSkipped 
= FALSE
; 
  41     mChildSkipped   
= FALSE
; 
  42     mContextMask    
= SP_CTX_ANY
; // FIXME:: should be an arg. 
  44     if ( sortContent 
&& !atContext
.IsSorted() ) 
  46         atContext
.SortMembers(); 
  48     mpCurCxt 
= &atContext
; // FIXME:: this is dirty, restoring it each time 
  50     if ( atContext
.GetContextType() & mContextMask 
) 
  52         atContext
.AcceptVisitor( *this ); 
  54     MMemberListT
& members 
= atContext
.GetMembers(); 
  56     for( size_t i 
= 0; i 
!= members
.size(); ++i 
) 
  58         if ( mSiblingSkipped 
) 
  64             size_t prevSz 
= members
.size(); 
  66             // visit members of the context recursivelly 
  67             VisitAll( *members
[i
], sortContent 
); 
  69             if ( members
.size() != prevSz 
) 
  71                 --i
; // current member was removed! 
  78 void spVisitor::RemoveCurrentContext() 
  80     if ( mpCurCxt
->GetParent() ) 
  82         mpCurCxt
->GetParent()->RemoveChild( mpCurCxt 
); 
  85 void spVisitor::SkipSiblings() 
  87     mSiblingSkipped 
= TRUE
; 
  90 void spVisitor::SkipChildren() 
  95 void spVisitor::SetFilter( int contextMask 
) 
  97     mContextMask 
= contextMask
; 
 100 /***** Implementation for class spComment *****/ 
 102 bool spComment::IsMultiline()  const 
 107 bool spComment::StartsParagraph() const 
 112 string
& spComment::GetText() 
 117 string 
spComment::GetText() const 
 122 /***** Implementation for class spContext *****/ 
 124 spContext::spContext() 
 127       mpFirstOccurence( NULL 
), 
 128       mAlreadySorted  ( FALSE 
), 
 141       mVisibility( SP_VIS_PRIVATE 
), 
 143       mIsVirtualContext         ( FALSE 
), 
 144       mVirtualContextHasChildren( FALSE 
), 
 149 void spContext::RemoveChildren() 
 151     for( size_t i 
= 0; i 
!= mMembers
.size(); ++i 
) 
 155     mMembers
.erase( mMembers
.begin(), mMembers
.end() ); 
 158 spContext::~spContext() 
 162     for( size_t i 
= 0; i 
!= mComments
.size(); ++i 
) 
 167 bool spContext::IsSorted() 
 169     return mAlreadySorted
; 
 172 void spContext::GetContextList( MMemberListT
& lst
, int contextMask 
) 
 174     for( size_t i 
= 0; i 
!= mMembers
.size(); ++i 
) 
 176         spContext
& member 
= *mMembers
[i
]; 
 178         if ( member
.GetContextType() & contextMask 
) 
 180             lst
.push_back( &member 
); 
 182         // collect required contexts recursively 
 183         member
.GetContextList( lst
, contextMask 
); 
 187 bool spContext::HasComments() 
 189     return ( mComments
.size() != 0 ); 
 192 void spContext::RemoveChild( spContext
* pChild 
) 
 194     for( size_t i 
= 0; i 
!= mMembers
.size(); ++i 
) 
 196         if ( mMembers
[i
] == pChild 
) 
 198             mMembers
.erase( &mMembers
[i
] ); 
 204     // the given child should exist on the parent's list  
 208 spContext
* spContext::GetEnclosingContext( int mask 
) 
 210     spContext
* cur 
= this->GetParent(); 
 212     while ( cur 
&& !(cur
->GetContextType() & mask
) )  
 214         cur 
= cur
->GetParent(); 
 219 bool spContext::PositionIsKnown() 
 221     return ( mSrcOffset 
!= (-1) && mContextLength 
!= (-1) ); 
 224 bool spContext::IsVirtualContext() 
 226     return mIsVirtualContext
; 
 229 bool spContext::VitualContextHasChildren() 
 231     return mVirtualContextHasChildren
; 
 234 string 
spContext::GetVirtualContextBody() 
 236     wxASSERT( mIsVirtualContext 
); 
 238     return mVirtualContextBody
; 
 241 string 
spContext::GetFooterOfVirtualContextBody() 
 243     wxASSERT( mIsVirtualContext 
); 
 245     return mVittualContextFooter
; 
 249 void spContext::SetVirtualContextBody( const string
& body
,  
 251                                        const string
& footer 
) 
 253     mVirtualContextHasChildren 
= hasChildren
; 
 255     mVirtualContextBody   
= body
; 
 256     mVittualContextFooter 
= footer
; 
 258     // atuomaticllay becomes virtual context 
 260     mIsVirtualContext   
= TRUE
; 
 263 string 
spContext::GetBody( spContext
* pCtx 
) 
 265     if ( ( pCtx 
== NULL 
|| pCtx 
== this ) && mIsVirtualContext 
)  
 267         return mVirtualContextBody
; 
 271         return GetParent()->GetBody( ( pCtx 
!= NULL 
) ? pCtx 
: this ); 
 273         return ""; // source-fragment cannot be found 
 276 string 
spContext::GetHeader( spContext
* pCtx 
) 
 280         return GetParent()->GetHeader( ( pCtx 
!= NULL 
) ? pCtx 
: this ); 
 282         return ""; // source-fragment cannot be found 
 285 bool spContext::IsFirstOccurence() 
 287     return ( mpFirstOccurence 
!= 0 ); 
 290 spContext
* spContext::GetFirstOccurence() 
 292     // this object should not itself be  
 293     // the first occurence of the context 
 294     wxASSERT( mpFirstOccurence 
!= 0 ); 
 296     return mpFirstOccurence
; 
 299 void spContext::AddMember( spContext
* pMember 
) 
 301     mMembers
.push_back( pMember 
); 
 303     pMember
->mpParent 
= this; 
 306 void spContext::AddComment( spComment
* pComment 
) 
 308     mComments
.push_back( pComment 
); 
 311 MMemberListT
& spContext::GetMembers() 
 316 spContext
* spContext::FindContext( const string
& identifier
, 
 318                                    bool  searchSubMembers
 
 321     for( size_t i 
= 0; i 
!= mMembers
.size(); ++i 
) 
 323         spContext
& member 
= *mMembers
[i
]; 
 325         if ( member
.GetName() == identifier 
&&  
 326              ( contextType 
& member
.GetContextType() ) 
 331         if ( searchSubMembers 
) 
 334                 member
.FindContext( identifier
, contextType
, 1 ); 
 336             if ( result 
) return result
; 
 343 void spContext::RemoveThisContext() 
 346         mpParent
->RemoveChild( this ); 
 348         // context should have a parent 
 349         wxFAIL_MSG("Context should have a parent"); 
 352 spContext
* spContext::GetOutterContext() 
 357 bool spContext::HasOutterContext() 
 359     return ( mpParent 
!= 0 ); 
 362 bool spContext::IsInFile() 
 364     return ( GetOutterContext()->GetContextType() == SP_CTX_FILE 
); 
 367 bool spContext::IsInNameSpace() 
 369     return ( GetOutterContext()->GetContextType() == SP_CTX_NAMESPACE 
); 
 372 bool spContext::IsInClass() 
 374     return ( GetOutterContext()->GetContextType() == SP_CTX_CLASS 
); 
 377 bool spContext::IsInOperation() 
 379     return ( GetOutterContext()->GetContextType() == SP_CTX_OPERATION 
); 
 382 spClass
& spContext::GetClass() 
 384     wxASSERT( GetOutterContext()->GetType() == SP_CTX_CLASS 
); 
 385     return *((spClass
*)mpParent 
); 
 388 spFile
& spContext::GetFile() 
 390     wxASSERT( GetOutterContext()->GetType() == SP_CTX_FILE 
); 
 391     return *((spFile
*)mpParent 
); 
 394 spNameSpace
& spContext::GetNameSpace() 
 396     wxASSERT( GetOutterContext()->GetType() == SP_CTX_NAMESPACE 
); 
 397     return *((spNameSpace
*)mpParent 
); 
 400 spOperation
& spContext::GetOperation() 
 402     wxASSERT( GetOutterContext()->GetType() == SP_CTX_OPERATION 
); 
 403     return *((spOperation
*)mpParent 
); 
 406 /***** Implementation for class spClass *****/ 
 408 void spClass::SortMembers() 
 413 /***** Implementation for class spOperation *****/ 
 415 spOperation::spOperation() 
 417     : mHasDefinition( FALSE 
) 
 421     mHasDefinition 
= false; 
 424 string 
spOperation::GetFullName(MarkupTagsT tags
) 
 426     string txt 
= tags
[TAG_BOLD
].start 
+ mRetType
; 
 430     txt 
+= tags
[TAG_BOLD
].end
; 
 432     for( size_t i 
= 0; i 
!= mMembers
.size(); ++i 
) 
 435         wxASSERT( mMembers
[i
]->GetContextType() == SP_CTX_PARAMETER 
); 
 437         spParameter
& param 
= *((spParameter
*)mMembers
[i
]); 
 442         txt 
+= tags
[TAG_BOLD
].start
; 
 446         txt 
+= tags
[TAG_BOLD
].end
; 
 447         txt 
+= tags
[TAG_ITALIC
].start
; 
 452         if ( param
.mInitVal 
!= "" ) 
 455             txt 
+= tags
[TAG_BOLD
].start
; 
 457             txt 
+= param
.mInitVal
; 
 459             txt 
+= tags
[TAG_BOLD
].end
; 
 462         txt 
+= tags
[TAG_ITALIC
].end
;; 
 465     txt 
+= tags
[TAG_BOLD
].start
; 
 467     txt 
+= tags
[TAG_BOLD
].end
; 
 469     // TBD:: constantness of method 
 474 /***** Implemenentation for class spPreprocessorLine *****/ 
 476 string 
spPreprocessorLine::CPP_GetIncludedFileNeme() const 
 478     wxASSERT( GetStatementType() == SP_PREP_DEF_INCLUDE_FILE 
); 
 482     while( i 
< mLine
.length() && mLine
[i
] != '"' && mLine
[i
] != '<' )  
 490     while( i 
< mLine
.length() && mLine
[i
] != '"' && mLine
[i
] != '>' )  
 494     if ( start 
< mLine
.length() ) 
 497         fname
.append( mLine
, start
, ( i 
- start 
) ); 
 502         return ""; // syntax error probably 
 507 /***** Implemenentation for class SourceParserBase *****/ 
 509 SourceParserBase::SourceParserBase() 
 517 SourceParserBase::~SourceParserBase() 
 519     if ( mpFileBuf 
) free( mpFileBuf 
); 
 521     if ( mpPlugin 
) delete mpPlugin
; 
 524 spFile
* SourceParserBase::ParseFile( const char* fname 
) 
 526     // FIXME:: the below should not be fixed! 
 528     const size_t MAX_BUF_SIZE 
= 1024*256; 
 530     if ( !mpFileBuf 
) mpFileBuf 
= (char*)malloc( MAX_BUF_SIZE 
); 
 532     mFileBufSz 
= MAX_BUF_SIZE
; 
 534     FILE* fp 
= fopen( fname
, "rt" ); 
 536     if ( (int)fp 
== -1 || !fp 
) return NULL
; 
 538     int sz 
= fread( mpFileBuf
, 1, mFileBufSz
, fp 
); 
 540     return Parse( mpFileBuf
, mpFileBuf 
+ sz 
); 
 543 void SourceParserBase::SetPlugin( SourceParserPlugin
* pPlugin 
) 
 545     if ( mpPlugin 
) delete mpPlugin
; 
 550 // =========================================================================== 
 552 // =========================================================================== 
 556 void spContext::Dump(const wxString
& indent
) const 
 560     // increase it for the children 
 561     wxString indentChild 
= indent 
+ "    "; 
 563     for ( MMemberListT::const_iterator i 
= mMembers
.begin(); 
 566         (*i
)->Dump(indentChild
); 
 570 void spContext::DumpThis(const wxString
& indent
) const 
 572     wxFAIL_MSG("abstract base class can't be found in parser tree!"); 
 575 void spParameter::DumpThis(const wxString
& indent
) const 
 577     wxLogDebug("%sparam named '%s' of type '%s'", 
 578                indent
.c_str(), mName
.c_str(), mType
.c_str()); 
 581 void spAttribute::DumpThis(const wxString
& indent
) const 
 583     wxLogDebug("%svariable named '%s' of type '%s'", 
 584                indent
.c_str(), mName
.c_str(), mType
.c_str()); 
 587 void spOperation::DumpThis(const wxString
& indent
) const 
 591         switch ( mVisibility 
) { 
 593                 protection 
= "public"; 
 596             case SP_VIS_PROTECTED
: 
 597                 protection 
= "protected"; 
 601                 protection 
= "private"; 
 605                 wxFAIL_MSG("unknown protection type"); 
 609         protection 
= "global"; 
 612     wxLogDebug("%s%s%s%s function named '%s::%s' of type '%s'", 
 614                mIsConstant 
? "const " : "", 
 615                mIsVirtual 
? "virtual " : "", 
 617                mScope
.c_str(), mName
.c_str(), mRetType
.c_str()); 
 620 void spPreprocessorLine::DumpThis(const wxString
& indent
) const 
 623     switch ( mDefType 
) { 
 624         case SP_PREP_DEF_DEFINE_SYMBOL
: 
 628         case SP_PREP_DEF_REDEFINE_SYMBOL
: 
 632         case SP_PREP_DEF_INCLUDE_FILE
: 
 633             kind
.Printf("include (%s)", CPP_GetIncludedFileNeme().c_str()); 
 636         case SP_PREP_DEF_OTHER
: 
 642     wxLogDebug("%spreprocessor statement: %s", 
 643                indent
.c_str(), kind
.c_str()); 
 646 void spClass::DumpThis(const wxString
& indent
) const 
 649     for ( StrListT::const_iterator i 
= mSuperClassNames
.begin(); 
 650           i 
!= mSuperClassNames
.end(); 
 661     switch ( mClassSubType 
) { 
 662         case SP_CLTYPE_CLASS
: 
 666         case SP_CLTYPE_TEMPLATE_CLASS
: 
 667             kind 
= "template class"; 
 670         case SP_CLTYPE_STRUCTURE
: 
 674         case SP_CLTYPE_UNION
: 
 678         case SP_CLTYPE_INTERFACE
: 
 683             wxFAIL_MSG("unknown class subtype"); 
 686     wxLogDebug("%s%s named '%s' (base classes: %s)", 
 687                indent
.c_str(), kind
.c_str(), 
 688                mName
.c_str(), base
.c_str()); 
 691 void spEnumeration::DumpThis(const wxString
& indent
) const 
 693     wxLogDebug("%senum named '%s'", 
 694                indent
.c_str(), mName
.c_str()); 
 697 void spTypeDef::DumpThis(const wxString
& indent
) const 
 699     wxLogDebug("%stypedef %s = %s", 
 700                indent
.c_str(), mName
.c_str(), mOriginalType
.c_str()); 
 703 void spFile::DumpThis(const wxString
& indent
) const 
 705     wxLogDebug("%sfile '%s'", 
 706                indent
.c_str(), mFileName
.c_str()); 
 709 #endif // __WXDEBUG__