[PATCH] D136012: [clang][Interp] Fix record members of reference type

Timm Bäder via Phabricator via cfe-commits cfe-commits at lists.llvm.org
Fri Oct 21 06:37:28 PDT 2022


tbaeder updated this revision to Diff 469580.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D136012/new/

https://reviews.llvm.org/D136012

Files:
  clang/lib/AST/Interp/ByteCodeExprGen.cpp
  clang/lib/AST/Interp/ByteCodeStmtGen.cpp
  clang/lib/AST/Interp/Interp.h
  clang/test/AST/Interp/references.cpp


Index: clang/test/AST/Interp/references.cpp
===================================================================
--- clang/test/AST/Interp/references.cpp
+++ clang/test/AST/Interp/references.cpp
@@ -88,3 +88,29 @@
   return j;
 }
 static_assert(RefToMemberExpr() == 11, "");
+
+struct Ref {
+  int &a;
+};
+
+constexpr int RecordWithRef() {
+  int m = 100;
+  Ref r{m};
+  m = 200;
+  return r.a;
+}
+static_assert(RecordWithRef() == 200, "");
+
+
+struct Ref2 {
+  int &a;
+  constexpr Ref2(int &a) : a(a) {}
+};
+
+constexpr int RecordWithRef2() {
+  int m = 100;
+  Ref2 r(m);
+  m = 200;
+  return r.a;
+}
+static_assert(RecordWithRef2() == 200, "");
Index: clang/lib/AST/Interp/Interp.h
===================================================================
--- clang/lib/AST/Interp/Interp.h
+++ clang/lib/AST/Interp/Interp.h
@@ -483,6 +483,8 @@
   return true;
 }
 
+/// 1) Peeks a pointer on the stack
+/// 2) Pushes the value of the pointer's field on the stack
 template <PrimType Name, class T = typename PrimConv<Name>::T>
 bool GetField(InterpState &S, CodePtr OpPC, uint32_t I) {
   const Pointer &Obj = S.Stk.peek<Pointer>();
@@ -512,6 +514,8 @@
   return true;
 }
 
+/// 1) Pops a pointer from the stack
+/// 2) Pushes the value of the pointer's field on the stack
 template <PrimType Name, class T = typename PrimConv<Name>::T>
 bool GetFieldPop(InterpState &S, CodePtr OpPC, uint32_t I) {
   const Pointer &Obj = S.Stk.pop<Pointer>();
Index: clang/lib/AST/Interp/ByteCodeStmtGen.cpp
===================================================================
--- clang/lib/AST/Interp/ByteCodeStmtGen.cpp
+++ clang/lib/AST/Interp/ByteCodeStmtGen.cpp
@@ -104,7 +104,7 @@
       if (const FieldDecl *Member = Init->getMember()) {
         const Record::Field *F = R->getField(Member);
 
-        if (Optional<PrimType> T = this->classify(InitExpr->getType())) {
+        if (Optional<PrimType> T = this->classify(InitExpr)) {
           if (!this->emitThis(InitExpr))
             return false;
 
Index: clang/lib/AST/Interp/ByteCodeExprGen.cpp
===================================================================
--- clang/lib/AST/Interp/ByteCodeExprGen.cpp
+++ clang/lib/AST/Interp/ByteCodeExprGen.cpp
@@ -392,6 +392,8 @@
     const Record *R = getRecord(RD);
     const Record::Field *F = R->getField(FD);
     // Leave a pointer to the field on the stack.
+    if (F->Decl->getType()->isReferenceType())
+      return this->emitGetFieldPop(PT_Ptr, F->Offset, E);
     return this->emitGetPtrField(F->Offset, E);
   }
 
@@ -862,7 +864,7 @@
       if (!this->emitDupPtr(Initializer))
         return false;
 
-      if (Optional<PrimType> T = classify(Init->getType())) {
+      if (Optional<PrimType> T = classify(Init)) {
         if (!this->visit(Init))
           return false;
 


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D136012.469580.patch
Type: text/x-patch
Size: 2787 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/cfe-commits/attachments/20221021/319f23d4/attachment.bin>


More information about the cfe-commits mailing list