@@ -1222,20 +1222,22 @@ namespace Cpp {
12221222    return  0 ;
12231223  }
12241224
1225-   intptr_t  GetVariableOffset (compat::Interpreter& I, Decl* D) {
1225+   intptr_t  GetVariableOffset (compat::Interpreter& I, Decl* D,
1226+                              CXXRecordDecl* BaseCXXRD) {
12261227    if  (!D)
12271228      return  0 ;
12281229
12291230    auto & C = I.getSema ().getASTContext ();
12301231
12311232    if  (auto * FD = llvm::dyn_cast<FieldDecl>(D)) {
1232-       const   clang::RecordDecl* RD  = FD->getParent ();
1233+       clang::RecordDecl* FieldParentRecordDecl  = FD->getParent ();
12331234      intptr_t  offset =
12341235          C.toCharUnitsFromBits (C.getFieldOffset (FD)).getQuantity ();
1235-       while  (RD->isAnonymousStructOrUnion ()) {
1236-         const  clang::RecordDecl* anon = RD;
1237-         RD = llvm::dyn_cast<RecordDecl>(anon->getParent ());
1238-         for  (auto  F = RD->field_begin (); F != RD->field_end (); ++F) {
1236+       while  (FieldParentRecordDecl->isAnonymousStructOrUnion ()) {
1237+         clang::RecordDecl* anon = FieldParentRecordDecl;
1238+         FieldParentRecordDecl = llvm::dyn_cast<RecordDecl>(anon->getParent ());
1239+         for  (auto  F = FieldParentRecordDecl->field_begin ();
1240+              F != FieldParentRecordDecl->field_end (); ++F) {
12391241          const  auto * RT = F->getType ()->getAs <RecordType>();
12401242          if  (!RT)
12411243            continue ;
@@ -1246,6 +1248,46 @@ namespace Cpp {
12461248        }
12471249        offset += C.toCharUnitsFromBits (C.getFieldOffset (FD)).getQuantity ();
12481250      }
1251+       if  (BaseCXXRD && BaseCXXRD != FieldParentRecordDecl) {
1252+         //  FieldDecl FD belongs to some class C, but the base class BaseCXXRD is
1253+         //  not C. That means BaseCXXRD derives from C. Offset needs to be
1254+         //  calculated for Derived class
1255+ 
1256+         //  Depth first Search is performed to the class that declears FD from
1257+         //  the base class
1258+         std::vector<CXXRecordDecl*> stack;
1259+         std::map<CXXRecordDecl*, CXXRecordDecl*> direction;
1260+         stack.push_back (BaseCXXRD);
1261+         while  (stack.size ()) {
1262+           CXXRecordDecl* RD = stack.back ();
1263+           stack.pop_back ();
1264+           size_t  num_bases = GetNumBases (RD);
1265+           bool  flag = false ;
1266+           for  (size_t  i = 0 ; i < num_bases; i++) {
1267+             auto * CRD = static_cast <CXXRecordDecl*>(GetBaseClass (RD, i));
1268+             direction[CRD] = RD;
1269+             if  (CRD == FieldParentRecordDecl) {
1270+               flag = true ;
1271+               break ;
1272+             }
1273+             stack.push_back (CRD);
1274+           }
1275+           if  (flag)
1276+             break ;
1277+         }
1278+         if  (auto * RD = llvm::dyn_cast<CXXRecordDecl>(FieldParentRecordDecl)) {
1279+           //  add in the offsets for the (multi level) base classes
1280+           while  (BaseCXXRD != RD) {
1281+             CXXRecordDecl* Parent = direction.at (RD);
1282+             offset += C.getASTRecordLayout (Parent)
1283+                           .getBaseClassOffset (RD)
1284+                           .getQuantity ();
1285+             RD = Parent;
1286+           }
1287+         } else  {
1288+           assert (false  && " Unreachable" 
1289+         }
1290+       }
12491291      return  offset;
12501292    }
12511293
@@ -1321,9 +1363,11 @@ namespace Cpp {
13211363    return  0 ;
13221364  }
13231365
1324-   intptr_t  GetVariableOffset (TCppScope_t var) {
1366+   intptr_t  GetVariableOffset (TCppScope_t var, TCppScope_t parent ) {
13251367    auto * D = static_cast <Decl*>(var);
1326-     return  GetVariableOffset (getInterp (), D);
1368+     auto * RD =
1369+         llvm::dyn_cast_or_null<CXXRecordDecl>(static_cast <Decl*>(parent));
1370+     return  GetVariableOffset (getInterp (), D, RD);
13271371  }
13281372
13291373  //  Check if the Access Specifier of the variable matches the provided value.
0 commit comments