Hello cfe-users,

I'm working to get my the libobjc2 Objective-C runtime working on Linux with 
clang-3.8.0.  I'm running into a problem with a library of mine that does class 
introspection.  My ObjC code does type introspection by looping through the 
ivars of an object and calling ivar_getTypeEncoding on each to get the type of 
the ivar.  When I compile with gcc, the ivar type for non-primitive variables 
comes through as @"NSString", @"NSDictionary", etc.  This also works with clang 
on my Mac.  But when I compile with clang on Linux, I only get the @ character. 
 I verified that the call to class_copyIvarList on Linux does return a list of 
Ivar objects, but when I call ivar_getTypeEncoding on those objects on Linux, I 
only get @, rather than the class name.  I've copied my library's ObjC code 
below.  

I talked this over with the owners of libobjc2, and we were wondering if there 
is a flag I can pass to clang to instruct it to emit this class data.  I looked 
at lib/CodeGen/CGObjCGNU.cpp in the clang source tree, but it wasn't 
immediately clear what flag I could pass here.  It's possible that there's no 
such flag, and the non-Apple clang simply doesn't emit this data, but I'd be 
somewhat surprised if Apple had diverged that much.

Thanks in advance for any help you can give,

David

My library's introspection code, with a debug print statement:

Ivar *ivarList = class_copyIvarList(c, &ivarCount);
for (i = 0; i < ivarCount; i++) {
  Ivar ivar = ivarList[i];
  const char *ivarCname = ivar_getName(ivar);
  if (ivarCname != 0 && ivarCname[0] != '_') {
     NSString *ivarName = [NSString stringWithUTF8String:ivarCname];
     const char *ivarType = ivar_getTypeEncoding(ivar);                    
     if (ivarType[0] == '@' && ivarType[1] == '"') {
         NSString *className = [[[NSString alloc] initWithBytes: &ivarType[2]
                              length: strlen(&ivarType[2])-1
                         encoding: NSUTF8StringEncoding] autorelease];
         Class c = NSClassFromString(className);
         if (c == nil) {
             NSLog(@"WARNING: unknown class name \"%@\" in declaration of %@", 
className, [self class]);
         } else {
             NSLog(@"DBG: Deduced class %@ from className %@", c, className);

With gcc and clang on the Mac, I get messages like this:

2016-09-14 19:29:21.950 archiveserver[1015:1015] DBG: Deduced class NSSet from 
className NSSet
2016-09-14 19:29:21.950 archiveserver[1015:1015] DBG: Deduced class NSString 
from className NSString
2016-09-14 19:29:21.950 archiveserver[1015:1015] DBG: Deduced class NSString 
from className NSString
2016-09-14 19:29:21.950 archiveserver[1015:1015] DBG: Deduced class NSString 
from className NSString
2016-09-14 19:29:21.950 archiveserver[1015:1015] DBG: Deduced class 
NSDictionary from className NSDictionary
2016-09-14 19:29:21.950 archiveserver[1015:1015] DBG: Deduced class 
NSDictionary from className NSDictionary
2016-09-14 19:29:21.950 archiveserver[1015:1015] DBG: Deduced class NSArray 
from className NSArray

With clang on Linux, nothing is printed, because ivarType[1] is not a double 
quote, so the second if evaluates to false.



_______________________________________________
cfe-users mailing list
cfe-users@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-users

Reply via email to