tbaeder created this revision. tbaeder added reviewers: aaron.ballman, erichkeane, tahonermann, shafik. Herald added a project: All. tbaeder requested review of this revision. Herald added a project: clang. Herald added a subscriber: cfe-commits.
There is a difference between a `Pointer` and a "`Pointer` to the first element of an array". Repository: rG LLVM Github Monorepo https://reviews.llvm.org/D137082 Files: clang/lib/AST/Interp/Interp.h clang/test/AST/Interp/arrays.cpp Index: clang/test/AST/Interp/arrays.cpp =================================================================== --- clang/test/AST/Interp/arrays.cpp +++ clang/test/AST/Interp/arrays.cpp @@ -42,6 +42,12 @@ return *(Arr + index); } +constexpr int derefPtr(const int *d) { + return *d; +} +static_assert(derefPtr(data) == 5, ""); + + static_assert(getElement(data, 1) == 4, ""); static_assert(getElement(data, 4) == 1, ""); Index: clang/lib/AST/Interp/Interp.h =================================================================== --- clang/lib/AST/Interp/Interp.h +++ clang/lib/AST/Interp/Interp.h @@ -949,7 +949,12 @@ const Pointer &Ptr = S.Stk.peek<Pointer>(); if (!CheckLoad(S, OpPC, Ptr)) return false; - S.Stk.push<T>(Ptr.deref<T>()); + // When getting the first value of an array, we need to offset to the + // first element. + if (Ptr.inArray() && Ptr.isRoot()) + S.Stk.push<T>(Ptr.atIndex(0).deref<T>()); + else + S.Stk.push<T>(Ptr.deref<T>()); return true; } @@ -958,7 +963,12 @@ const Pointer &Ptr = S.Stk.pop<Pointer>(); if (!CheckLoad(S, OpPC, Ptr)) return false; - S.Stk.push<T>(Ptr.deref<T>()); + // When getting the first value of an array, we need to offset to the + // first element. + if (Ptr.inArray() && Ptr.isRoot()) + S.Stk.push<T>(Ptr.atIndex(0).deref<T>()); + else + S.Stk.push<T>(Ptr.deref<T>()); return true; }
Index: clang/test/AST/Interp/arrays.cpp =================================================================== --- clang/test/AST/Interp/arrays.cpp +++ clang/test/AST/Interp/arrays.cpp @@ -42,6 +42,12 @@ return *(Arr + index); } +constexpr int derefPtr(const int *d) { + return *d; +} +static_assert(derefPtr(data) == 5, ""); + + static_assert(getElement(data, 1) == 4, ""); static_assert(getElement(data, 4) == 1, ""); Index: clang/lib/AST/Interp/Interp.h =================================================================== --- clang/lib/AST/Interp/Interp.h +++ clang/lib/AST/Interp/Interp.h @@ -949,7 +949,12 @@ const Pointer &Ptr = S.Stk.peek<Pointer>(); if (!CheckLoad(S, OpPC, Ptr)) return false; - S.Stk.push<T>(Ptr.deref<T>()); + // When getting the first value of an array, we need to offset to the + // first element. + if (Ptr.inArray() && Ptr.isRoot()) + S.Stk.push<T>(Ptr.atIndex(0).deref<T>()); + else + S.Stk.push<T>(Ptr.deref<T>()); return true; } @@ -958,7 +963,12 @@ const Pointer &Ptr = S.Stk.pop<Pointer>(); if (!CheckLoad(S, OpPC, Ptr)) return false; - S.Stk.push<T>(Ptr.deref<T>()); + // When getting the first value of an array, we need to offset to the + // first element. + if (Ptr.inArray() && Ptr.isRoot()) + S.Stk.push<T>(Ptr.atIndex(0).deref<T>()); + else + S.Stk.push<T>(Ptr.deref<T>()); return true; }
_______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits