On 9/16/23 17:41, Patrick Palka wrote:
On Sat, 16 Sep 2023, Jason Merrill wrote:

On 9/15/23 12:03, Patrick Palka wrote:
Bootstrapped and regtested on x86_64-pc-linux-gnu, does this look OK for
trunk?

-- >8 --

Here convert_to_void always completes the type of an INDIRECT_REF or
VAR_DECL expression, but according to [expr.context] an lvalue-to-rvalue
conversion is applied to a discarded-value expression only if "the
expression is a glvalue of volatile-qualified type".  This patch restricts
convert_to_void's type completion accordingly.

        PR c++/111419

gcc/cp/ChangeLog:

        * cvt.cc (convert_to_void) <case INDIRECT_REF>: Only call
        complete_type if the type is volatile and the INDIRECT_REF
        isn't an implicit one.

Hmm, what does implicit have to do with it?  The expression forms listed in
https://eel.is/c++draft/expr.context#2 include "id-expression"...

When there's an implicit INDIRECT_REF, I reckoned the type of the
id-expression is really a reference type, which can't be cv-qualified?

A name can have reference type, but its use as an expression doesn't:
https://eel.is/c++draft/expr.type#1.sentence-1

diff --git a/gcc/testsuite/g++.dg/expr/discarded1a.C
b/gcc/testsuite/g++.dg/expr/discarded1a.C
new file mode 100644
index 00000000000..5516ff46fe9
--- /dev/null
+++ b/gcc/testsuite/g++.dg/expr/discarded1a.C
@@ -0,0 +1,16 @@
+// PR c++/111419
+
+struct Incomplete;
+
+template<class T, int> struct Holder { T t; }; // { dg-error "incomplete" }
+
+extern volatile Holder<Incomplete, 0> a;
+extern volatile Holder<Incomplete, 1>& b;
+extern volatile Holder<Incomplete, 2>* c;
+
+int main() {
+  a; // { dg-message "required from here" }
+  b; // { dg-warning "implicit dereference will not access object" }
+     // { dg-bogus "required from here" "" { target *-*-* } .-1 }

...so it seems to me this line should get the lvalue-rvalue conversion (and
not the warning about no access).

+  *c; // { dg-message "required from here" }
+}

Reply via email to