[clang] [clang][Interp] Implement compound assign operators on bitfields (PR #67306)

Timm Baeder via cfe-commits cfe-commits at lists.llvm.org
Tue Oct 10 04:52:16 PDT 2023


https://github.com/tbaederr updated https://github.com/llvm/llvm-project/pull/67306

>From d275b2de769bbae45c87c9ae7e04d744b4849c91 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Timm=20B=C3=A4der?= <tbaeder at redhat.com>
Date: Mon, 25 Sep 2023 11:39:02 +0200
Subject: [PATCH] [clang][Interp] Implement compound assign operators on
 bitfields

---
 clang/lib/AST/Interp/ByteCodeExprGen.cpp |  7 ++++-
 clang/test/AST/Interp/bitfields.cpp      | 38 ++++++++++++++++++++++--
 2 files changed, 42 insertions(+), 3 deletions(-)

diff --git a/clang/lib/AST/Interp/ByteCodeExprGen.cpp b/clang/lib/AST/Interp/ByteCodeExprGen.cpp
index e7a431ddee6f002..182c04fdd349f57 100644
--- a/clang/lib/AST/Interp/ByteCodeExprGen.cpp
+++ b/clang/lib/AST/Interp/ByteCodeExprGen.cpp
@@ -1158,8 +1158,13 @@ bool ByteCodeExprGen<Emitter>::VisitCompoundAssignOperator(
   }
 
   // And store the result in LHS.
-  if (DiscardResult)
+  if (DiscardResult) {
+    if (LHS->refersToBitField())
+      return this->emitStoreBitFieldPop(*ResultT, E);
     return this->emitStorePop(*ResultT, E);
+  }
+  if (LHS->refersToBitField())
+    return this->emitStoreBitField(*ResultT, E);
   return this->emitStore(*ResultT, E);
 }
 
diff --git a/clang/test/AST/Interp/bitfields.cpp b/clang/test/AST/Interp/bitfields.cpp
index e078704fce51ff0..9a144e2f0d9610e 100644
--- a/clang/test/AST/Interp/bitfields.cpp
+++ b/clang/test/AST/Interp/bitfields.cpp
@@ -31,8 +31,6 @@ namespace Basic {
     return a.a = 10;
   }
   static_assert(storeA2() == 2, "");
-
-  // TODO: +=, -=, etc. operators.
 }
 
 namespace Overflow {
@@ -45,3 +43,39 @@ namespace Overflow {
 
   static_assert(f() == 3, "");
 }
+
+namespace Compound {
+  struct A {
+    unsigned int a : 2;
+    constexpr A() : a(0) {}
+    constexpr A(int a) : a(a) {}
+  };
+
+  constexpr unsigned add() {
+    A a;
+    a.a += 10;
+    return a.a;
+  }
+  static_assert(add() == 2, "");
+
+  constexpr unsigned sub() {
+    A a;
+    a.a -= 10;
+    return a.a;
+  }
+  static_assert(sub() == 2, "");
+
+  constexpr unsigned mul() {
+    A a(1);
+    a.a *= 5;
+    return a.a;
+  }
+  static_assert(mul() == 1, "");
+
+  constexpr unsigned div() {
+    A a(2);
+    a.a /= 2;
+    return a.a;
+  }
+  static_assert(div() == 1, "");
+}



More information about the cfe-commits mailing list