================
@@ -2260,8 +2260,69 @@ mlir::Value 
CIRGenModule::emitMemberPointerConstant(const UnaryOperator *e) {
   // Otherwise, a member data pointer.
   auto ty = mlir::cast<cir::DataMemberType>(convertType(e->getType()));
   const auto *fieldDecl = cast<FieldDecl>(decl);
-  return cir::ConstantOp::create(
-      builder, loc, builder.getDataMemberAttr(ty, fieldDecl->getFieldIndex()));
+  const auto *mpt = e->getType()->castAs<MemberPointerType>();
+  const auto *destClass = mpt->getMostRecentCXXRecordDecl();
+  std::optional<llvm::SmallVector<int32_t>> path =
+      buildMemberPath(destClass, fieldDecl);
+  if (!path)
+    return {};
+  return cir::ConstantOp::create(builder, loc,
+                                 builder.getDataMemberAttr(ty, *path));
+}
+
+std::optional<llvm::SmallVector<int32_t>>
+CIRGenModule::buildMemberPath(const CXXRecordDecl *destClass,
+                              const FieldDecl *field) {
+  llvm::SmallVector<int32_t> path;
+  if (!findFieldMemberPath(destClass, field, path))
+    return std::nullopt;
+  return path;
+}
+
+bool CIRGenModule::findFieldMemberPath(const CXXRecordDecl *currentClass,
+                                       const FieldDecl *field,
+                                       llvm::SmallVectorImpl<int32_t> &path) {
+  const CIRGenRecordLayout &layout =
+      getTypes().getCIRGenRecordLayout(currentClass);
+
+  for (const FieldDecl *fd : currentClass->fields()) {
+    if (fd != field)
----------------
erichkeane wrote:

Why is this whole loop required?  You're skipping it if the `fd` `!=` the 
`field`, but the only context you have is the `field` anyway.  Isn't this loop 
entirely unnecessary?  As far as "is `field` inside of `currentClass`, you can 
use `field->getParent()`.

https://github.com/llvm/llvm-project/pull/200854
_______________________________________________
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to