[cfe-dev] Matching Indirect base classes

Pedro Delgado Perez pedro.delgado at uca.es
Mon Nov 11 09:52:09 PST 2013


 
Thank you so much Daniel, it works in the way I needed!

If it's not asking too much, I still have two little doubts:

- Do you know what the "4" is used in the SmallPtrSet for?
llvm::SmallPtrSet<const CXXRecordDecl*, 4> Bases;
 - In a case like the following:

class A{
...
};

class B: private A{
...
};

class C: public B{
...
}

>From the class C, if I would like to not include the base class A becuase its access is private, how could I do that? With base_class_iterator [ http://clang.llvm.org/doxygen/classclang_1_1CXXRecordDecl.html#aa88e7e85c5b2e83c34a69a8d65abafb2 ] I obtained a CXXBaseSpecifier, but now I have the classes themselves.

Thanks again,

Pedro.

El día 11 nov 2013 16:43, Daniel Jasper <djasper at google.com> escribió:
> 
> 
> 
> 
> 
> On Mon, Nov 11, 2013 at 2:04 AM, Pedro Delgado Perez <pedro.delgado at uca.es [ mailto:pedro.delgado at uca.es ]> wrote:
> 
> 
> Well, using as reference what you named of Sema::CheckUsingDeclQualifier, I tried the following;
> 
> DeclarationMatcher I_Matcher = recordDecl().bind("var");
> 
> class HVD : public MatchFinder::MatchCallback {
> public :
> 
>  llvm::SmallPtrSet<const CXXRecordDecl*, 4> Bases;
>  
>  static bool collect(const CXXRecordDecl *Base, void *OpaqueData) {
>      HVD *Data = reinterpret_cast<HVD*>(OpaqueData);
>      Data->Bases.insert(Base);
>      return true;
>  }
>  
>  virtual void run(const MatchFinder::MatchResult &Result) {
>      ... ....
>     if (const CXXRecordDecl *FS = Result.Nodes.getNodeAs<clang::CXXRecordDecl>("var")){
>         if(FS->forallBases(collect, this)){
>              for(llvm::SmallPtrSet<const CXXRecordDecl*, 4>::const_iterator i = Bases.begin(); i != Bases.end(); i++){
>                  ... ... 
>              }
>        }
>     }
>  }
> };
> 
> 1 - To tell you the truth, I have no idea what I have to do with OpaqueData. Is what I put above correct?
> 
The OpaqueData part seems correct. 

2 - I got an error doing this and I can't understand the problem.

IHD_operator: /home/pedro/clang-llvm/llvm/tools/clang/include/clang/AST/DeclCXX.h:558: const clang::CXXRecordDecl::DefinitionData& clang::CXXRecordDecl::data() const: Assertion `DefinitionData && "queried property of class with no definition"' failed.
Stack dump:
0.   <eof> parser at end of file

As per its comment, forallBases needs to be called on a CXXRecordDecl that is a definition (not e.g. a forward declaration or an injected class name). Thus, you will need to ensure that FS->getDefinition() is not NULL and then call it on that.

3. Once inside the for loop, how can I get each object CXXRecordDecl through SmallPtrSetIterator. [ http://llvm.org/docs/doxygen/html/classllvm_1_1SmallPtrSetIterator.html#ac931fc62430140f2cce08d72e5f27c82 ]

I think you just need to dereference it:
const CXXRecordDecl *Base = *i;

Thanks for your time,

Pedro.

No problem, I hope this helps,
Daniel
 

El día 08 nov 2013 18:30, Daniel Jasper <djasper at google.com [ mailto:djasper at google.com ]> escribió:


Yes, sorry, lookupInBases() is what I meant. You'll need forAllBases(). You can pass in a ForallBasesCallback, which is basically a callback function executed for each base class.
I have not used this myself, but for an example, look at:
CXXRecordDecl::isProvablyNotDerivedFrom defined in lib/AST/CXXInheritance.cpp.


Also lib/Sema/SemaDeclCXX.cpp has an example close to the bottom of Sema::CheckUsingDeclQualifier()
that collects all of the bases into a SmallPtrSet.



On Fri, Nov 8, 2013 at 9:16 AM, Pedro Delgado Perez <pedro.delgado at uca.es [ mailto:pedro.delgado at uca.es ]> wrote:


Hi,

Thanks Daniel, I suppose you mean CXXRecordDecl::lookupInBases() instead CXXRecordDecl::findInBases().

Have you ever used one of these methods? I don't understand quite well how can I use them for my purpose. What I need is that, given an object CXXRecordDecl, I can analyze something in particular in each one of its base classes (direct or indirect). Thus, I need to get each one of these classes to process them, but the methods you refer only return a bool.

Could you please show me an example using these methods? Mainly, with respect the arguments passed to these methdos.

Thanks,

Pedro.

El día 08 nov 2013 15:32, Daniel Jasper <djasper at google.com [ mailto:djasper at google.com ]> escribió:


Take a look at CXXRecordDecl::forallBases() and CXXRecordDecl::findInBases(). Dependent on what you want to do, one of them might do what you need.
Cheers,
Daniel



On Fri, Nov 8, 2013 at 2:39 AM, Pedro Delgado Perez <pedro.delgado at uca.es [ mailto:pedro.delgado at uca.es ]> wrote:


Hello,

Please, I need some help with an issue I noticed a few days ago and I am not able to solve.

To illustrate my problem, I show this piece of code:

class A{
   public:
      A(): a(1) {};
      int a;
};

class B: public A{
   public:
      B(): b(2){};
      int b;
};

class C: public B{
   public:
      C(): c(3){};
      int b;
      int a;
};

We have three classes, where:
B inherits directly from A
C inherits directly from B and INDIRECTLY from A

Using CXXRecordDecl::base_class_iterator, the classes indirectly inherited are not visited. Please, can someone explain me how to take into account these indirectly inherited base classes? I've been thinking on recursion (use base_class_iterator on each class directly inherited), but I'm sure there should be another simpler way to do this.

Thanks in advance,

Pedro.


_______________________________________________
cfe-dev mailing list
cfe-dev at cs.uiuc.edu [ mailto:cfe-dev at cs.uiuc.edu ]

http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev [ http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev ]


-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/cfe-dev/attachments/20131111/79372c7b/attachment.html>


More information about the cfe-dev mailing list