[gcc/devel/rust/master] gccrs: refactoring rust_error_at "redefined multiple times"
https://gcc.gnu.org/g:9554470e7f876f8b05f2620ecca376c319191d1d commit 9554470e7f876f8b05f2620ecca376c319191d1d Author: Sri Ganesh Thota Date: Tue Mar 25 18:30:58 2025 +0530 gccrs: refactoring rust_error_at "redefined multiple times" gcc/rust/ChangeLog: * resolve/rust-ast-resolve-base.h (redefined_error): created a function for rust_error_at for redefined at multiple times. * resolve/rust-ast-resolve-implitem.h: changed rust_error_at to redefined_error. * resolve/rust-ast-resolve-stmt.cc (ResolveStmt::visit): changed rust_error_at to redefined_error. * resolve/rust-ast-resolve-stmt.h: changed rust_error_at to redefined_error. * resolve/rust-ast-resolve-toplevel.h: changed rust_error_at to redefined_error. Signed-off-by: Sri Ganesh Thota Diff: --- gcc/rust/resolve/rust-ast-resolve-base.h | 5 + gcc/rust/resolve/rust-ast-resolve-implitem.h | 19 - gcc/rust/resolve/rust-ast-resolve-stmt.cc| 2 +- gcc/rust/resolve/rust-ast-resolve-stmt.h | 20 - gcc/rust/resolve/rust-ast-resolve-toplevel.h | 32 ++-- 5 files changed, 41 insertions(+), 37 deletions(-) diff --git a/gcc/rust/resolve/rust-ast-resolve-base.h b/gcc/rust/resolve/rust-ast-resolve-base.h index 7f01d503d8c6..33f01ef5693d 100644 --- a/gcc/rust/resolve/rust-ast-resolve-base.h +++ b/gcc/rust/resolve/rust-ast-resolve-base.h @@ -27,6 +27,11 @@ namespace Rust { namespace Resolver { +inline void +redefined_error (const rich_location &loc) +{ + rust_error_at (loc, "redefined multiple times"); +} class ResolverBase : public AST::ASTVisitor { diff --git a/gcc/rust/resolve/rust-ast-resolve-implitem.h b/gcc/rust/resolve/rust-ast-resolve-implitem.h index f924816c3280..ffd198cd686c 100644 --- a/gcc/rust/resolve/rust-ast-resolve-implitem.h +++ b/gcc/rust/resolve/rust-ast-resolve-implitem.h @@ -51,7 +51,7 @@ public: [&] (const CanonicalPath &, NodeId, location_t locus) -> void { rich_location r (line_table, type.get_locus ()); r.add_range (locus); - rust_error_at (r, "defined multiple times"); + redefined_error (r); }); } @@ -67,7 +67,7 @@ public: [&] (const CanonicalPath &, NodeId, location_t locus) -> void { rich_location r (line_table, constant.get_locus ()); r.add_range (locus); - rust_error_at (r, "defined multiple times"); + redefined_error (r); }); } @@ -84,7 +84,7 @@ public: [&] (const CanonicalPath &, NodeId, location_t locus) -> void { rich_location r (line_table, function.get_locus ()); r.add_range (locus); - rust_error_at (r, "defined multiple times"); + redefined_error (r); }); } @@ -124,7 +124,7 @@ public: [&] (const CanonicalPath &, NodeId, location_t locus) -> void { rich_location r (line_table, function.get_locus ()); r.add_range (locus); - rust_error_at (r, "defined multiple times"); + redefined_error (r); }); mappings.insert_canonical_path (function.get_node_id (), cpath); @@ -144,7 +144,7 @@ public: [&] (const CanonicalPath &, NodeId, location_t locus) -> void { rich_location r (line_table, constant.get_locus ()); r.add_range (locus); - rust_error_at (r, "defined multiple times"); + redefined_error (r); }); mappings.insert_canonical_path (constant.get_node_id (), cpath); @@ -162,7 +162,7 @@ public: [&] (const CanonicalPath &, NodeId, location_t locus) -> void { rich_location r (line_table, type.get_locus ()); r.add_range (locus); - rust_error_at (r, "defined multiple times"); + redefined_error (r); }); mappings.insert_canonical_path (type.get_node_id (), cpath); @@ -202,7 +202,7 @@ public: [&] (const CanonicalPath &, NodeId, location_t locus) -> void { rich_location r (line_table, function.get_locus ()); r.add_range (locus); - rust_error_at (r, "defined multiple times"); + redefined_error (r); }); NodeId current_module = resolver->peek_current_module_scope (); @@ -221,7 +221,7 @@ public: [&] (const CanonicalPath &, NodeId, location_t locus) -> void { rich_location r (line_table, item.get_locus ()); r.add_range (locus); - rust_error_at (r, "defined multiple times"); + redefined_error (r); }); NodeId current_module = resolver->peek_current_module_scope (); @@ -239,8 +239,7 @@ public: [&] (const CanonicalPath &, NodeId, location_t locus) -> void { rich_location r (line_table, type.get_locus ()); r.add_range (locus); - - rust_error_at (r, "defined multiple times"); + redefined_error (r); }); NodeId current_module = resolver->peek_current_module_scope (); diff --git a/gcc/rust/resolve/rust-ast-resolve-stmt.cc b/gcc/rust/r
[gcc/devel/rust/master] nr2.0: Adjust test issue-2812.rs
https://gcc.gnu.org/g:22bf192a72383a1f41d92a833487b1eacbe30446 commit 22bf192a72383a1f41d92a833487b1eacbe30446 Author: Owen Avery Date: Mon Mar 24 18:27:41 2025 -0400 nr2.0: Adjust test issue-2812.rs gcc/testsuite/ChangeLog: * rust/compile/issue-2812.rs: Avoid multiple definition error. * rust/compile/nr2/exclude: Remove issue-2812.rs. Signed-off-by: Owen Avery Diff: --- gcc/testsuite/rust/compile/issue-2812.rs | 4 ++-- gcc/testsuite/rust/compile/nr2/exclude | 1 - 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/gcc/testsuite/rust/compile/issue-2812.rs b/gcc/testsuite/rust/compile/issue-2812.rs index 173259b12914..0de1738309f1 100644 --- a/gcc/testsuite/rust/compile/issue-2812.rs +++ b/gcc/testsuite/rust/compile/issue-2812.rs @@ -1,4 +1,4 @@ // { dg-additional-options "-frust-compile-until=astvalidation" } fn foo_1(&self); -fn foo_1(&mut self); -fn foo_1(self); +fn foo_2(&mut self); +fn foo_3(self); diff --git a/gcc/testsuite/rust/compile/nr2/exclude b/gcc/testsuite/rust/compile/nr2/exclude index 665e0cf4d99b..9502f3981912 100644 --- a/gcc/testsuite/rust/compile/nr2/exclude +++ b/gcc/testsuite/rust/compile/nr2/exclude @@ -1,7 +1,6 @@ canonical_paths1.rs cfg1.rs generics9.rs -issue-2812.rs issue-3315-2.rs lookup_err1.rs macros/mbe/macro6.rs
[gcc r15-9277] gccrs: Fix ICE when resolving lifetimes without name
https://gcc.gnu.org/g:4f110b297d4e764df001099b1fb647dddf8ac278 commit r15-9277-g4f110b297d4e764df001099b1fb647dddf8ac278 Author: Philip Herron Date: Mon Mar 31 17:33:59 2025 +0100 gccrs: Fix ICE when resolving lifetimes without name We dont need to assert here the lifetime code already supports this case. Fixes Rust-GCC#3657 gcc/rust/ChangeLog: * typecheck/rust-hir-type-check-base.cc: remove assertion gcc/testsuite/ChangeLog: * rust/compile/issue-3657.rs: New test. Signed-off-by: Philip Herron Diff: --- gcc/rust/typecheck/rust-hir-type-check-base.cc | 2 -- gcc/testsuite/rust/compile/issue-3657.rs | 8 2 files changed, 8 insertions(+), 2 deletions(-) diff --git a/gcc/rust/typecheck/rust-hir-type-check-base.cc b/gcc/rust/typecheck/rust-hir-type-check-base.cc index 34a726cc6650..d3d688217348 100644 --- a/gcc/rust/typecheck/rust-hir-type-check-base.cc +++ b/gcc/rust/typecheck/rust-hir-type-check-base.cc @@ -397,8 +397,6 @@ TypeCheckBase::resolve_generic_params ( auto lifetime_param = static_cast (*generic_param); auto lifetime = lifetime_param.get_lifetime (); - rust_assert (lifetime.get_lifetime_type () -== AST::Lifetime::LifetimeType::NAMED); context->get_lifetime_resolver ().insert_mapping ( context->intern_lifetime (lifetime)); } diff --git a/gcc/testsuite/rust/compile/issue-3657.rs b/gcc/testsuite/rust/compile/issue-3657.rs new file mode 100644 index ..978f3ce336fb --- /dev/null +++ b/gcc/testsuite/rust/compile/issue-3657.rs @@ -0,0 +1,8 @@ +struct Foo<'_>(&'_ u8); + +impl Foo<'a> { +// { dg-error "unresolved lifetime" "" { target *-*-* } .-1 } +fn x() {} +} + +fn x() {}
[gcc r15-9309] nvptx: In offloading compilation, special-case certain host-setup symbol aliases: avoid unused label
https://gcc.gnu.org/g:175016de6f9d800343ce31cf1837a3265569b657 commit r15-9309-g175016de6f9d800343ce31cf1837a3265569b657 Author: Thomas Schwinge Date: Mon Apr 7 12:39:33 2025 +0200 nvptx: In offloading compilation, special-case certain host-setup symbol aliases: avoid unused label 'emit_ptx_alias' diagnostic Minor fix-up for commit 65b31b3fff2fced015ded1026733605f34053796 "nvptx: In offloading compilation, special-case certain host-setup symbol aliases [PR101544]", as of which we see for non-offloading configurations: +[...]/source-gcc/gcc/config/nvptx/nvptx.cc: In function 'void nvptx_asm_output_def_from_decls(FILE*, tree, tree)': +[...]/source-gcc/gcc/config/nvptx/nvptx.cc:7769:2: warning: label 'emit_ptx_alias' defined but not used [-Wunused-label] + 7769 | emit_ptx_alias: + | ^~ gcc/ * config/nvptx/nvptx.cc (nvptx_asm_output_def_from_decls) [!ACCEL_COMPILER]: Don't define label 'emit_ptx_alias'. Diff: --- gcc/config/nvptx/nvptx.cc | 2 ++ 1 file changed, 2 insertions(+) diff --git a/gcc/config/nvptx/nvptx.cc b/gcc/config/nvptx/nvptx.cc index de0ce5d91645..87364bf423c5 100644 --- a/gcc/config/nvptx/nvptx.cc +++ b/gcc/config/nvptx/nvptx.cc @@ -7766,7 +7766,9 @@ nvptx_asm_output_def_from_decls (FILE *stream, tree name, return; } +#ifdef ACCEL_COMPILER emit_ptx_alias: +#endif cgraph_node *cnode = cgraph_node::get (name); if (!cnode->referred_to_p ())
[gcc r15-9311] GCN, nvptx: Define '_Unwind_RaiseException', '_Unwind_Resume_or_Rethrow'
https://gcc.gnu.org/g:54ab0f6785c006ddff056dab9c0240cddae82020 commit r15-9311-g54ab0f6785c006ddff056dab9c0240cddae82020 Author: Thomas Schwinge Date: Tue Mar 18 10:10:30 2025 +0100 GCN, nvptx: Define '_Unwind_RaiseException', '_Unwind_Resume_or_Rethrow' This resolves GCN: ld: error: undefined symbol: _Unwind_RaiseException >>> referenced by eh_throw.cc:93 ([...]/source-gcc/libstdc++-v3/libsupc++/eh_throw.cc:93) >>> eh_throw.o:(__cxa_throw) in archive /srv/data/tschwinge/amd-instinct2/gcc/build/submit-light-target_gcn/build-gcc/amdgcn-amdhsa/gfx908/libstdc++-v3/src/.libs/libstdc++.a [...] collect2: error: ld returned 1 exit status ..., and/or: ld: error: undefined symbol: _Unwind_Resume_or_Rethrow >>> referenced by eh_throw.cc:129 ([...]/source-gcc/libstdc++-v3/libsupc++/eh_throw.cc:129) >>> eh_throw.o:(__cxa_rethrow) in archive /srv/data/tschwinge/amd-instinct2/gcc/build/submit-light-target_gcn/build-gcc/amdgcn-amdhsa/gfx908/libstdc++-v3/src/.libs/libstdc++.a [...] collect2: error: ld returned 1 exit status ..., and nvptx: unresolved symbol _Unwind_RaiseException collect2: error: ld returned 1 exit status ..., or: unresolved symbol _Unwind_Resume_or_Rethrow collect2: error: ld returned 1 exit status For both GCN, nvptx, this each progresses ~25 'check-gcc-c++', and ~10 'check-target-libstdc++-v3' test cases: [-FAIL:-]{+PASS:+} [...] (test for excess errors) ..., with (if applicable, for most of them): [-UNRESOLVED:-]{+PASS:+} [...] [-compilation failed to produce executable-]{+execution test+} ..., or some 'FAIL: [...] execution test' where these test cases now FAIL when attempting to use these interfaces, or, if applicable, FAIL due to run-time 'GCC/nvptx: sorry, unimplemented: dynamic stack allocation not supported'. libgcc/ * config/gcn/unwind-gcn.c (_Unwind_RaiseException) (_Unwind_Resume_or_Rethrow): New. * config/nvptx/unwind-nvptx.c (_Unwind_RaiseException) (_Unwind_Resume_or_Rethrow): Likewise. Diff: --- libgcc/config/gcn/unwind-gcn.c | 14 ++ libgcc/config/nvptx/unwind-nvptx.c | 14 ++ 2 files changed, 28 insertions(+) diff --git a/libgcc/config/gcn/unwind-gcn.c b/libgcc/config/gcn/unwind-gcn.c index e014cc08243c..eae741c55bbb 100644 --- a/libgcc/config/gcn/unwind-gcn.c +++ b/libgcc/config/gcn/unwind-gcn.c @@ -24,6 +24,13 @@ #include "unwind.h" +_Unwind_Reason_Code +_Unwind_RaiseException(struct _Unwind_Exception *exc __attribute__ ((__unused__))) +{ + __builtin_abort (); + return 0; +} + void _Unwind_DeleteException (struct _Unwind_Exception *exc) { @@ -31,6 +38,13 @@ _Unwind_DeleteException (struct _Unwind_Exception *exc) (*exc->exception_cleanup) (_URC_FOREIGN_EXCEPTION_CAUGHT, exc); } +_Unwind_Reason_Code +_Unwind_Resume_or_Rethrow (struct _Unwind_Exception *exc __attribute__ ((__unused__))) +{ + __builtin_abort (); + return 0; +} + _Unwind_Reason_Code _Unwind_Backtrace(_Unwind_Trace_Fn trace, void * trace_argument) { diff --git a/libgcc/config/nvptx/unwind-nvptx.c b/libgcc/config/nvptx/unwind-nvptx.c index e014cc08243c..eae741c55bbb 100644 --- a/libgcc/config/nvptx/unwind-nvptx.c +++ b/libgcc/config/nvptx/unwind-nvptx.c @@ -24,6 +24,13 @@ #include "unwind.h" +_Unwind_Reason_Code +_Unwind_RaiseException(struct _Unwind_Exception *exc __attribute__ ((__unused__))) +{ + __builtin_abort (); + return 0; +} + void _Unwind_DeleteException (struct _Unwind_Exception *exc) { @@ -31,6 +38,13 @@ _Unwind_DeleteException (struct _Unwind_Exception *exc) (*exc->exception_cleanup) (_URC_FOREIGN_EXCEPTION_CAUGHT, exc); } +_Unwind_Reason_Code +_Unwind_Resume_or_Rethrow (struct _Unwind_Exception *exc __attribute__ ((__unused__))) +{ + __builtin_abort (); + return 0; +} + _Unwind_Reason_Code _Unwind_Backtrace(_Unwind_Trace_Fn trace, void * trace_argument) {
[gcc r15-9310] GCN, nvptx: Define '_Unwind_DeleteException'
https://gcc.gnu.org/g:815abd68353751d53ed9299e218f8ca1cc108d5f commit r15-9310-g815abd68353751d53ed9299e218f8ca1cc108d5f Author: Thomas Schwinge Date: Tue Mar 18 10:10:30 2025 +0100 GCN, nvptx: Define '_Unwind_DeleteException' This resolves GCN: ld: error: undefined symbol: _Unwind_DeleteException >>> referenced by eh_catch.cc:109 ([...]/source-gcc/libstdc++-v3/libsupc++/eh_catch.cc:109) >>> eh_catch.o:(__cxa_end_catch) in archive [...]/build-gcc/amdgcn-amdhsa/libstdc++-v3/src/.libs/libstdc++.a [...] collect2: error: ld returned 1 exit status ..., and nvptx: unresolved symbol _Unwind_DeleteException collect2: error: ld returned 1 exit status For both GCN, nvptx, this each progresses ~100 'check-gcc-c++', and ~500 'check-target-libstdc++-v3' test cases: [-FAIL:-]{+PASS:+} [...] (test for excess errors) ..., with (if applicable, for most of them): [-UNRESOLVED:-]{+PASS:+} [...] [-compilation failed to produce executable-]{+execution test+} ..., or just a few 'FAIL: [...] execution test' where these test cases now FAIL for unrelated reasons, or, if applicable, FAIL due to run-time 'GCC/nvptx: sorry, unimplemented: dynamic stack allocation not supported'. libgcc/ * config/gcn/unwind-gcn.c (_Unwind_DeleteException): New. * config/nvptx/unwind-nvptx.c (_Unwind_DeleteException): Likewise. Diff: --- libgcc/config/gcn/unwind-gcn.c | 7 +++ libgcc/config/nvptx/unwind-nvptx.c | 7 +++ 2 files changed, 14 insertions(+) diff --git a/libgcc/config/gcn/unwind-gcn.c b/libgcc/config/gcn/unwind-gcn.c index 44657ae992bd..e014cc08243c 100644 --- a/libgcc/config/gcn/unwind-gcn.c +++ b/libgcc/config/gcn/unwind-gcn.c @@ -24,6 +24,13 @@ #include "unwind.h" +void +_Unwind_DeleteException (struct _Unwind_Exception *exc) +{ + if (exc->exception_cleanup) +(*exc->exception_cleanup) (_URC_FOREIGN_EXCEPTION_CAUGHT, exc); +} + _Unwind_Reason_Code _Unwind_Backtrace(_Unwind_Trace_Fn trace, void * trace_argument) { diff --git a/libgcc/config/nvptx/unwind-nvptx.c b/libgcc/config/nvptx/unwind-nvptx.c index 44657ae992bd..e014cc08243c 100644 --- a/libgcc/config/nvptx/unwind-nvptx.c +++ b/libgcc/config/nvptx/unwind-nvptx.c @@ -24,6 +24,13 @@ #include "unwind.h" +void +_Unwind_DeleteException (struct _Unwind_Exception *exc) +{ + if (exc->exception_cleanup) +(*exc->exception_cleanup) (_URC_FOREIGN_EXCEPTION_CAUGHT, exc); +} + _Unwind_Reason_Code _Unwind_Backtrace(_Unwind_Trace_Fn trace, void * trace_argument) {
[gcc/devel/rust/master] feature: Add min_specialization feature
https://gcc.gnu.org/g:9684625ab897b3ff322642d99563bac64b1383b7 commit 9684625ab897b3ff322642d99563bac64b1383b7 Author: Arthur Cohen Date: Tue Apr 1 17:45:00 2025 +0200 feature: Add min_specialization feature gcc/rust/ChangeLog: * checks/errors/rust-feature.cc (Feature::create): Handle `#![feature(min_specialization)]`. * checks/errors/rust-feature.h: Likewise. Diff: --- gcc/rust/checks/errors/rust-feature.cc | 4 gcc/rust/checks/errors/rust-feature.h | 1 + 2 files changed, 5 insertions(+) diff --git a/gcc/rust/checks/errors/rust-feature.cc b/gcc/rust/checks/errors/rust-feature.cc index 04872613d114..d7484e5357f2 100644 --- a/gcc/rust/checks/errors/rust-feature.cc +++ b/gcc/rust/checks/errors/rust-feature.cc @@ -55,6 +55,9 @@ Feature::create (Feature::Name f) "1.11.0", 37854); case Feature::Name::PRELUDE_IMPORT: return Feature (f, Feature::State::ACTIVE, "prelude_import", "1.0.0"); +case Feature::Name::MIN_SPECIALIZATION: + return Feature (f, Feature::State::ACTIVE, "min_specialization", + "1.0.0" /* FIXME: What version here? */, 31844); case Feature::Name::AUTO_TRAITS: return Feature (f, Feature::State::ACTIVE, "optin_builtin_traits", "1.0.0", 13231); @@ -80,6 +83,7 @@ const std::map Feature::name_hash_map = { {"raw_ref_op", Feature::Name::RAW_REF_OP}, {"exclusive_range_pattern", Feature::Name::EXCLUSIVE_RANGE_PATTERN}, {"prelude_import", Feature::Name::PRELUDE_IMPORT}, + {"min_specialization", Feature::Name::MIN_SPECIALIZATION}, }; // namespace Rust tl::optional diff --git a/gcc/rust/checks/errors/rust-feature.h b/gcc/rust/checks/errors/rust-feature.h index a078dbda4d28..be592671587e 100644 --- a/gcc/rust/checks/errors/rust-feature.h +++ b/gcc/rust/checks/errors/rust-feature.h @@ -51,6 +51,7 @@ public: RAW_REF_OP, EXCLUSIVE_RANGE_PATTERN, PRELUDE_IMPORT, +MIN_SPECIALIZATION, }; const std::string &as_string () { return m_name_str; }
[gcc r15-9296] gccrs: Migrate error state to optionals
https://gcc.gnu.org/g:827ceac9e1b7d95d353168f3f3a9e92f8091404f commit r15-9296-g827ceac9e1b7d95d353168f3f3a9e92f8091404f Author: Pierre-Emmanuel Patry Date: Tue Apr 1 19:55:28 2025 +0200 gccrs: Migrate error state to optionals gcc/rust/ChangeLog: * ast/rust-ast-builder.cc (Builder::self_ref_param): Remove error state and use optional. * ast/rust-ast-visitor.cc (DefaultASTVisitor::visit): Check label before visiting. * ast/rust-ast.cc (ContinueExpr::as_string): Retrieve label value. (Lifetime::as_string): Retrieve lifetime value. (ReferenceType::as_string): Likewise. (SelfParam::as_string): Likewise. * ast/rust-ast.h: Remove lifetime and LifetimeParam error state. * ast/rust-desugar-for-loops.cc (DesugarForLoops::DesugarCtx::make_break_arm): Use optional instead of error state. * ast/rust-expr.h (class ContinueExpr): Make label optional. * ast/rust-item.h (class SelfParam): Make lifetime optional. * ast/rust-type.h (class ReferenceType): Likewise. * backend/rust-compile-base.cc: Use optional for self param instead of error state. * backend/rust-compile-base.h: Update function prototype. * expand/rust-derive-clone.cc (DeriveClone::clone_fn): Use optional. * hir/rust-ast-lower-base.cc (ASTLoweringBase::lower_self): Lower lifetime only if it exists. * hir/rust-ast-lower-block.h: Lower loop label only if it exists. * hir/rust-ast-lower-expr.cc (ASTLoweringExpr::visit): Likewise. * hir/rust-ast-lower-implitem.cc (ASTLowerImplItem::visit): Remove references to error state. (ASTLowerTraitItem::visit): Lower self param only if it exists. * hir/rust-ast-lower-item.cc (ASTLoweringItem::visit): Use nullopt for default value instead of SelfParam error state. * hir/rust-ast-lower.cc (ASTLoweringExprWithBlock::visit): Lower label only if it exists. * hir/rust-hir-dump.cc (Dump::do_traitfunctiondecl): Print self only if it exists. (Dump::visit): Liewise. * hir/tree/rust-hir-bound.h: Remove error state. * hir/tree/rust-hir-expr.cc (ContinueExpr::ContinueExpr): Use optional in constructor for loop label. (BreakExpr::BreakExpr): Likewise. * hir/tree/rust-hir-expr.h (class ContinueExpr): Remove error state implementation. (class BreakExpr): Likewise. * hir/tree/rust-hir-generic-param.h: Likewise. * hir/tree/rust-hir-item.cc (SelfParam::SelfParam): Make lifetime optional. (Function::Function): Make self param optional. * hir/tree/rust-hir-item.h (class Function): Likewise. * hir/tree/rust-hir-type.cc (ReferenceType::ReferenceType): Make lifetime optional. * hir/tree/rust-hir-type.h (class ReferenceType): Likewise. * hir/tree/rust-hir.cc (ContinueExpr::as_string): Use new getter. (BreakExpr::as_string): Likewise. (Lifetime::as_string): Likewise. (ReferenceType::as_string): Likewise. (TraitFunctionDecl::as_string): Likewise. (SelfParam::as_string): Remove error state checking. * parse/rust-parse-impl.h (Parser::parse_generic_param): Adapt to optional. (Parser::parse_lifetime_params): Likewise. (Parser::parse_lifetime_params_objs): Likewise. (Parser::parse_lifetime_param): Likewise. (Parser::parse_lifetime_where_clause_item): Likewise. (Parser::parse_type_param_bound): Likewise. (Parser::parse_lifetime_bounds): Likewise. (Parser::parse_path_generic_args): Likewise. (Parser::parse_self_param): Likewise. (Parser::parse_break_expr): Likewise. (Parser::parse_continue_expr): Likewise. (Parser::parse_reference_type_inner): Likewise. * parse/rust-parse.h (class ParseLifetimeParamError): Add new class for lifetime param parsing errors. (class ParseLifetimeError): Add new class for lifetime parsing errors. (enum ParseSelfError): Add new class for self param parsing errors. * typecheck/rust-hir-type-check-implitem.cc (TypeCheckImplItem::visit): Use unchecked getter in checked context. And make anonymous region. * typecheck/rust-hir-type-check.cc (TraitItemReference::get_type_from_fn): Likewise. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/rust/ast/rust-ast-builder.cc | 2 +- gcc/rust/ast/rust-ast-visitor.cc | 6 +- gcc/rust/ast/rust-ast.cc | 9 +- gcc/r
[gcc/devel/rust/master] gccrs: Fix recusive type query and nullptr on type path
https://gcc.gnu.org/g:67017c92b8cb51064243c9c76b0fafe3c80e17b2 commit 67017c92b8cb51064243c9c76b0fafe3c80e17b2 Author: Philip Herron Date: Wed Apr 2 18:21:46 2025 +0100 gccrs: Fix recusive type query and nullptr on type path This was a small fix to sort out the segfault to check for nullptr on the TypePath cases for query type. But when this happened opened up a few bugs that were hidden under the carpet namely: compile/issue-2905-{1,2}.rs which has a recursive type query which needs to ne handled but now and error message is being output for the type path. This happens because we start resolving a generic struct: struct Wierd(A<(T,)>); So the child field A is also generic and the generic argument of the tuple of T needs to be applied to this generic field. This causes a chunk of code to do bounds checking to ensure the bounds are ok, this is also something that probably might change as generic types will have the bounds secified anyway but thats besides the case right now. So once this bounds checking occurs we endup looking at the impl block for Wierd which is also grand but we still havent finished resolving the parent type of Wierd which is recusive. But the query type system needs to check for that. The other issue was: compile/issue-3022.rs which is a resolution issue: impl, U> Foo for Bar The bound of Foo is added to T before U is resolved but this was hidden before the new error message was added. So now we have a generic arguements handler being used correctly all over the code base apart from 1 last case for Traits but we will deal with that later. This handles the case by setting up the type parameters upfront then sorting out their bounds. Fixes Rust-GCC#3625 gcc/rust/ChangeLog: * typecheck/rust-hir-trait-resolve.cc (TraitResolver::resolve_trait): new argument * typecheck/rust-hir-type-check-base.cc (TypeCheckBase::TypeCheckBase): new helper * typecheck/rust-hir-type-check-base.h: new helper prototype * typecheck/rust-hir-type-check-implitem.cc (TypeCheckTopLevelExternItem::visit): remove comment out code * typecheck/rust-hir-type-check-path.cc (TypeCheckExpr::resolve_root_path): check for null * typecheck/rust-hir-type-check-type.cc (TypeCheckType::resolve_root_path): likewise (TypeResolveGenericParam::Resolve): new args (TypeResolveGenericParam::ApplyAnyTraitBounds): new helper (TypeResolveGenericParam::apply_trait_bounds): new field (TypeResolveGenericParam::visit): update * typecheck/rust-hir-type-check-type.h: new args * typecheck/rust-hir-type-check.cc (TraitItemReference::get_type_from_fn): reuse helper * typecheck/rust-type-util.cc (query_type): check for recursive query * typecheck/rust-tyty-subst.cc (SubstitutionParamMapping::SubstitutionParamMapping): remove const (SubstitutionParamMapping::get_generic_param): likewise * typecheck/rust-tyty-subst.h: likewise * typecheck/rust-tyty-variance-analysis.cc (GenericTyVisitorCtx::process_type): likewise gcc/testsuite/ChangeLog: * rust/compile/issue-3625.rs: New test. Signed-off-by: Philip Herron Diff: --- gcc/rust/typecheck/rust-hir-trait-resolve.cc | 4 +- gcc/rust/typecheck/rust-hir-type-check-base.cc | 42 +- gcc/rust/typecheck/rust-hir-type-check-base.h | 8 +- gcc/rust/typecheck/rust-hir-type-check-implitem.cc | 163 + gcc/rust/typecheck/rust-hir-type-check-path.cc | 2 +- gcc/rust/typecheck/rust-hir-type-check-type.cc | 44 -- gcc/rust/typecheck/rust-hir-type-check-type.h | 11 +- gcc/rust/typecheck/rust-hir-type-check.cc | 33 + gcc/rust/typecheck/rust-type-util.cc | 37 + gcc/rust/typecheck/rust-tyty-subst.cc | 8 +- gcc/rust/typecheck/rust-tyty-subst.h | 6 +- gcc/rust/typecheck/rust-tyty-variance-analysis.cc | 2 +- gcc/testsuite/rust/compile/issue-3625.rs | 2 + 13 files changed, 144 insertions(+), 218 deletions(-) diff --git a/gcc/rust/typecheck/rust-hir-trait-resolve.cc b/gcc/rust/typecheck/rust-hir-trait-resolve.cc index e33a8d0788fa..1492839ce9d3 100644 --- a/gcc/rust/typecheck/rust-hir-trait-resolve.cc +++ b/gcc/rust/typecheck/rust-hir-trait-resolve.cc @@ -234,7 +234,9 @@ TraitResolver::resolve_trait (HIR::Trait *trait_reference) // The one exception is the implicit Self type of a trait bool apply_sized = !is_self; auto param_type - = TypeResolveGenericParam::Resolve (*generic_param, apply_sized); + = TypeResolveGenericParam::Resolve (*generic_param, true, +
[gcc/devel/rust/master] gccrs: Fix ICE on raw reference
https://gcc.gnu.org/g:314090971a51037bb77e36b46c7a10652b9e6c3f commit 314090971a51037bb77e36b46c7a10652b9e6c3f Author: Philip Herron Date: Thu Apr 3 15:39:58 2025 +0100 gccrs: Fix ICE on raw reference This patch adds support for raw references which enforce the pointer type away from a reference type. Fixes Rust-GCC#3667 gcc/rust/ChangeLog: * backend/rust-compile-base.cc (HIRCompileBase::address_expression): allow optional type * backend/rust-compile-base.h: update prototype * backend/rust-compile-expr.cc (CompileExpr::visit): update borrow expr * backend/rust-compile-extern.h: remove unused debug * backend/rust-compile-resolve-path.cc (HIRCompileBase::query_compile): update usage * hir/rust-ast-lower-expr.cc (ASTLoweringExpr::visit): lower raw ref * hir/tree/rust-hir-expr.cc (BorrowExpr::BorrowExpr): add flag for raw ref * hir/tree/rust-hir-expr.h (class BorrowExpr): add new raw ref field * typecheck/rust-hir-type-check-expr.cc (TypeCheckExpr::visit): add handle for raw ref gcc/testsuite/ChangeLog: * rust/compile/issue-3667.rs: New test. Signed-off-by: Philip Herron Diff: --- gcc/rust/backend/rust-compile-base.cc | 7 +-- gcc/rust/backend/rust-compile-base.h | 3 ++- gcc/rust/backend/rust-compile-expr.cc | 3 ++- gcc/rust/backend/rust-compile-extern.h | 6 -- gcc/rust/backend/rust-compile-resolve-path.cc | 4 ++-- gcc/rust/hir/rust-ast-lower-expr.cc| 11 --- gcc/rust/hir/tree/rust-hir-expr.cc | 4 ++-- gcc/rust/hir/tree/rust-hir-expr.h | 4 +++- gcc/rust/typecheck/rust-hir-type-check-expr.cc | 9 + gcc/testsuite/rust/compile/issue-3667.rs | 24 10 files changed, 53 insertions(+), 22 deletions(-) diff --git a/gcc/rust/backend/rust-compile-base.cc b/gcc/rust/backend/rust-compile-base.cc index f8c5fa99f795..04e3e75ed7d0 100644 --- a/gcc/rust/backend/rust-compile-base.cc +++ b/gcc/rust/backend/rust-compile-base.cc @@ -549,7 +549,7 @@ HIRCompileBase::mark_addressable (tree exp, location_t locus) } tree -HIRCompileBase::address_expression (tree expr, location_t location) +HIRCompileBase::address_expression (tree expr, location_t location, tree ptrty) { if (expr == error_mark_node) return error_mark_node; @@ -557,7 +557,10 @@ HIRCompileBase::address_expression (tree expr, location_t location) if (!mark_addressable (expr, location)) return error_mark_node; - return build_fold_addr_expr_loc (location, expr); + if (ptrty == NULL || ptrty == error_mark_node) +ptrty = build_pointer_type (TREE_TYPE (expr)); + + return build_fold_addr_expr_with_type_loc (location, expr, ptrty); } tree diff --git a/gcc/rust/backend/rust-compile-base.h b/gcc/rust/backend/rust-compile-base.h index 3ec1e2c6dffc..69f565cea2b4 100644 --- a/gcc/rust/backend/rust-compile-base.h +++ b/gcc/rust/backend/rust-compile-base.h @@ -29,7 +29,8 @@ class HIRCompileBase public: virtual ~HIRCompileBase () {} - static tree address_expression (tree expr, location_t locus); + static tree address_expression (tree expr, location_t locus, + tree ptrty = NULL_TREE); static tree compile_constant_expr ( Context *ctx, HirId coercion_id, TyTy::BaseType *resolved_type, diff --git a/gcc/rust/backend/rust-compile-expr.cc b/gcc/rust/backend/rust-compile-expr.cc index 47603484d06c..9dcec64f5b6a 100644 --- a/gcc/rust/backend/rust-compile-expr.cc +++ b/gcc/rust/backend/rust-compile-expr.cc @@ -905,7 +905,8 @@ CompileExpr::visit (HIR::BorrowExpr &expr) &tyty)) return; - translated = address_expression (main_expr, expr.get_locus ()); + tree expected_type = TyTyResolveCompile::compile (ctx, tyty); + translated = address_expression (main_expr, expr.get_locus (), expected_type); } void diff --git a/gcc/rust/backend/rust-compile-extern.h b/gcc/rust/backend/rust-compile-extern.h index a26ff2fb134b..aa4a0c3d1bcc 100644 --- a/gcc/rust/backend/rust-compile-extern.h +++ b/gcc/rust/backend/rust-compile-extern.h @@ -34,16 +34,10 @@ class CompileExternItem : public HIRCompileBase, public: static tree compile (HIR::ExternalItem *item, Context *ctx, TyTy::BaseType *concrete = nullptr, - bool is_query_mode = false, location_t ref_locus = UNDEF_LOCATION) { CompileExternItem compiler (ctx, concrete, ref_locus); item->accept_vis (compiler); - -if (is_query_mode && compiler.reference == error_mark_node) - rust_internal_error_at (ref_locus, "failed to compile extern item: %s", - item->as_string ().c_str ()); - return compiler.reference; } diff --git a/gcc/rust/backend/rust-compile-resolve-path.cc
[gcc/devel/rust/master] gccrs: Fix ICE when hitting invalid types for generics
https://gcc.gnu.org/g:8022ca11ed991cba51843c3226e4de9c2b795ecc commit 8022ca11ed991cba51843c3226e4de9c2b795ecc Author: Philip Herron Date: Wed Apr 2 21:02:44 2025 +0100 gccrs: Fix ICE when hitting invalid types for generics We need to check upfront if the type is valid or not. Then error with a decent message. Fixes Rust-GCC#3643 Fixes Rust-GCC#3646 Fixes Rust-GCC#3654 Fixes Rust-GCC#3663 Fixes Rust-GCC#3671 gcc/rust/ChangeLog: * resolve/rust-ast-resolve-type.cc (ResolveRelativeTypePath::go): fix error msg * typecheck/rust-substitution-mapper.cc (SubstMapper::Resolve): add validation (SubstMapper::valid_type): new check (SubstMapper::visit): check if can resolve * typecheck/rust-substitution-mapper.h: new prototype gcc/testsuite/ChangeLog: * rust/compile/nr2/exclude: nr2 is missing type path error * rust/compile/issue-3643.rs: New test. * rust/compile/issue-3646.rs: New test. * rust/compile/issue-3654.rs: New test. * rust/compile/issue-3663.rs: New test. * rust/compile/issue-3671.rs: New test. Signed-off-by: Philip Herron Diff: --- gcc/rust/resolve/rust-ast-resolve-type.cc | 2 +- gcc/rust/typecheck/rust-substitution-mapper.cc | 27 +- gcc/rust/typecheck/rust-substitution-mapper.h | 2 ++ gcc/testsuite/rust/compile/issue-3643.rs | 4 gcc/testsuite/rust/compile/issue-3646.rs | 7 +++ gcc/testsuite/rust/compile/issue-3654.rs | 3 +++ gcc/testsuite/rust/compile/issue-3663.rs | 6 ++ gcc/testsuite/rust/compile/issue-3671.rs | 2 ++ gcc/testsuite/rust/compile/nr2/exclude | 2 ++ 9 files changed, 53 insertions(+), 2 deletions(-) diff --git a/gcc/rust/resolve/rust-ast-resolve-type.cc b/gcc/rust/resolve/rust-ast-resolve-type.cc index c1c40227b4f3..135504ed9b5e 100644 --- a/gcc/rust/resolve/rust-ast-resolve-type.cc +++ b/gcc/rust/resolve/rust-ast-resolve-type.cc @@ -357,7 +357,7 @@ ResolveRelativeTypePath::go (AST::TypePath &path, NodeId &resolved_node_id) { rust_error_at (segment->get_locus (), ErrorCode::E0412, "could not resolve type path %qs", -segment->as_string ().c_str ()); +segment->get_ident_segment ().as_string ().c_str ()); return false; } } diff --git a/gcc/rust/typecheck/rust-substitution-mapper.cc b/gcc/rust/typecheck/rust-substitution-mapper.cc index 20fe8f04adcb..878c4d54a0a8 100644 --- a/gcc/rust/typecheck/rust-substitution-mapper.cc +++ b/gcc/rust/typecheck/rust-substitution-mapper.cc @@ -34,6 +34,15 @@ SubstMapper::Resolve (TyTy::BaseType *base, location_t locus, HIR::GenericArgs *generics, const std::vector ®ions) { + if (!valid_type (base)) +{ + rich_location r (line_table, locus); + r.add_fixit_remove (generics->get_locus ()); + rust_error_at (r, ErrorCode::E0109, +"generic arguments are not allowed for this type"); + return base; +} + SubstMapper mapper (base->get_ref (), generics, regions, locus); base->accept_vis (mapper); rust_assert (mapper.resolved != nullptr); @@ -46,6 +55,17 @@ SubstMapper::InferSubst (TyTy::BaseType *base, location_t locus) return SubstMapper::Resolve (base, locus, nullptr, {}); } +bool +SubstMapper::valid_type (TyTy::BaseType *base) +{ + bool is_fn = base->is (); + bool is_adt = base->is (); + bool is_placeholder = base->is (); + bool is_projection = base->is (); + + return is_fn || is_adt || is_placeholder || is_projection; +} + bool SubstMapper::have_generic_args () const { @@ -103,7 +123,12 @@ SubstMapper::visit (TyTy::ADTType &type) void SubstMapper::visit (TyTy::PlaceholderType &type) { - rust_assert (type.can_resolve ()); + if (!type.can_resolve ()) +{ + resolved = &type; + return; +} + resolved = SubstMapper::Resolve (type.resolve (), locus, generics, regions); } diff --git a/gcc/rust/typecheck/rust-substitution-mapper.h b/gcc/rust/typecheck/rust-substitution-mapper.h index a0aba567d24e..2f03e4b7b359 100644 --- a/gcc/rust/typecheck/rust-substitution-mapper.h +++ b/gcc/rust/typecheck/rust-substitution-mapper.h @@ -37,6 +37,8 @@ public: bool have_generic_args () const; + static bool valid_type (TyTy::BaseType *base); + void visit (TyTy::FnType &type) override; void visit (TyTy::ADTType &type) override; void visit (TyTy::PlaceholderType &type) override; diff --git a/gcc/testsuite/rust/compile/issue-3643.rs b/gcc/testsuite/rust/compile/issue-3643.rs new file mode 100644 index ..bed9ffc0c2b9 --- /dev/null +++ b/gcc/testsuite/rust/compile/issue-3643.rs @@ -0,0 +1,4 @@ +fn foo() { +let x: usize; +// { dg-error "generic arguments are not allowed for this type .E0109
[gcc/devel/rust/master] gccrs: Fix ICE on invalid match arms
https://gcc.gnu.org/g:002c349b6d0f8c12d26beaff178785524f155583 commit 002c349b6d0f8c12d26beaff178785524f155583 Author: Philip Herron Date: Thu Apr 3 15:37:40 2025 +0100 gccrs: Fix ICE on invalid match arms We hit assertions on empty enum or unknown variant, this catches the error and emits a new diagnostic. Fixes Rust-GCC#3656 gcc/rust/ChangeLog: * typecheck/rust-hir-type-check-pattern.cc (TypeCheckPattern::visit): emit error gcc/testsuite/ChangeLog: * rust/compile/issue-3656.rs: New test. Signed-off-by: Philip Herron Diff: --- gcc/rust/typecheck/rust-hir-type-check-pattern.cc | 21 +++-- gcc/testsuite/rust/compile/issue-3656.rs | 10 ++ 2 files changed, 29 insertions(+), 2 deletions(-) diff --git a/gcc/rust/typecheck/rust-hir-type-check-pattern.cc b/gcc/rust/typecheck/rust-hir-type-check-pattern.cc index eb3c4162bf46..1543d6212866 100644 --- a/gcc/rust/typecheck/rust-hir-type-check-pattern.cc +++ b/gcc/rust/typecheck/rust-hir-type-check-pattern.cc @@ -277,7 +277,15 @@ TypeCheckPattern::visit (HIR::StructPattern &pattern) infered = pattern_ty; TyTy::ADTType *adt = static_cast (infered); - rust_assert (adt->number_of_variants () > 0); + if (adt->number_of_variants () == 0) +{ + HIR::PathInExpression &path = pattern.get_path (); + const AST::SimplePath &sp = path.as_simple_path (); + rust_error_at (pattern.get_locus (), ErrorCode::E0574, +"expected struct, variant or union type, found enum %qs", +sp.as_string ().c_str ()); + return; +} TyTy::VariantDef *variant = adt->get_variants ().at (0); if (adt->is_enum ()) @@ -285,7 +293,16 @@ TypeCheckPattern::visit (HIR::StructPattern &pattern) HirId variant_id = UNKNOWN_HIRID; bool ok = context->lookup_variant_definition ( pattern.get_path ().get_mappings ().get_hirid (), &variant_id); - rust_assert (ok); + if (!ok) + { + HIR::PathInExpression &path = pattern.get_path (); + const AST::SimplePath &sp = path.as_simple_path (); + rust_error_at ( + pattern.get_locus (), ErrorCode::E0574, + "expected struct, variant or union type, found enum %qs", + sp.as_string ().c_str ()); + return; + } ok = adt->lookup_variant_by_id (variant_id, &variant); rust_assert (ok); diff --git a/gcc/testsuite/rust/compile/issue-3656.rs b/gcc/testsuite/rust/compile/issue-3656.rs new file mode 100644 index ..e0bec2fa4a69 --- /dev/null +++ b/gcc/testsuite/rust/compile/issue-3656.rs @@ -0,0 +1,10 @@ +enum Foo { +Bar(isize), +} + +fn main() { +match Foo::Bar(205) { +Foo { i } => (), +// { dg-error "expected struct, variant or union type, found enum .Foo. .E0574." "" { target *-*-* } .-1 } +} +}
[gcc/devel/rust/master] Add check for label
https://gcc.gnu.org/g:676e3eacc36a233dec52023faa9f3c78007bbabe commit 676e3eacc36a233dec52023faa9f3c78007bbabe Author: Pierre-Emmanuel Patry Date: Mon Mar 31 17:01:18 2025 +0200 Add check for label gcc/rust/ChangeLog: * ast/rust-ast-visitor.cc (DefaultASTVisitor::visit): Visit loop label only if it exists. gcc/testsuite/ChangeLog: * rust/compile/nr2/exclude: Remove passing test. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/rust/ast/rust-ast-visitor.cc | 3 ++- gcc/testsuite/rust/compile/nr2/exclude | 2 -- 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/gcc/rust/ast/rust-ast-visitor.cc b/gcc/rust/ast/rust-ast-visitor.cc index 2949f1cc81be..b5da001da5ac 100644 --- a/gcc/rust/ast/rust-ast-visitor.cc +++ b/gcc/rust/ast/rust-ast-visitor.cc @@ -568,7 +568,8 @@ DefaultASTVisitor::visit (AST::WhileLoopExpr &expr) { visit_outer_attrs (expr); visit (expr.get_predicate_expr ()); - visit (expr.get_loop_label ()); + if (expr.has_loop_label ()) +visit (expr.get_loop_label ()); visit (expr.get_loop_block ()); } diff --git a/gcc/testsuite/rust/compile/nr2/exclude b/gcc/testsuite/rust/compile/nr2/exclude index 76ef39f982d3..2f4585cbe8c4 100644 --- a/gcc/testsuite/rust/compile/nr2/exclude +++ b/gcc/testsuite/rust/compile/nr2/exclude @@ -23,8 +23,6 @@ derive-default1.rs derive-eq-invalid.rs derive-hash1.rs torture/alt_patterns1.rs -torture/loop4.rs -torture/loop8.rs torture/name_resolve1.rs issue-3568.rs issue-3663.rs
[gcc/devel/rust/master] gccrs: Fix ICE for reserved lifetime name
https://gcc.gnu.org/g:641f9a406118761f4399dc6e0636b2617bf90599 commit 641f9a406118761f4399dc6e0636b2617bf90599 Author: Philip Herron Date: Thu Apr 3 16:32:36 2025 +0100 gccrs: Fix ICE for reserved lifetime name This is a reserved name so this changes the assertion to a diagnostic. Fixes Rust-GCC#3647 gcc/rust/ChangeLog: * typecheck/rust-typecheck-context.cc (TypeCheckContext::lookup_lifetime): emit error gcc/testsuite/ChangeLog: * rust/compile/issue-3647.rs: New test. Signed-off-by: Philip Herron Diff: --- gcc/rust/typecheck/rust-typecheck-context.cc | 11 ++- gcc/testsuite/rust/compile/issue-3647.rs | 7 +++ 2 files changed, 17 insertions(+), 1 deletion(-) diff --git a/gcc/rust/typecheck/rust-typecheck-context.cc b/gcc/rust/typecheck/rust-typecheck-context.cc index 907833fba971..95c78a7008ec 100644 --- a/gcc/rust/typecheck/rust-typecheck-context.cc +++ b/gcc/rust/typecheck/rust-typecheck-context.cc @@ -514,7 +514,16 @@ TypeCheckContext::lookup_lifetime (const HIR::Lifetime &lifetime) const { if (lifetime.get_lifetime_type () == AST::Lifetime::NAMED) { - rust_assert (lifetime.get_name () != "static"); + if (lifetime.get_name () == "static") + { + rich_location r (line_table, lifetime.get_locus ()); + r.add_fixit_insert_after (lifetime.get_locus (), + "static is a reserved lifetime name"); + rust_error_at (r, ErrorCode::E0262, +"invalid lifetime parameter name: %qs", +lifetime.get_name ().c_str ()); + return tl::nullopt; + } const auto name = lifetime.get_name (); auto it = lifetime_name_interner.find (name); if (it == lifetime_name_interner.end ()) diff --git a/gcc/testsuite/rust/compile/issue-3647.rs b/gcc/testsuite/rust/compile/issue-3647.rs new file mode 100644 index ..51d9478d7b1e --- /dev/null +++ b/gcc/testsuite/rust/compile/issue-3647.rs @@ -0,0 +1,7 @@ +#![allow(dead_code)] +type A = fn(); + +type B = for<'static> fn(); +// { dg-error "invalid lifetime parameter name: .static. .E0262." "" { target *-*-* } .-1 } + +pub fn main() {}
[gcc/devel/rust/master] Remove unused error constructor and getter
https://gcc.gnu.org/g:75b7b7c210c62405a29068826d5ebb67ac6d6d68 commit 75b7b7c210c62405a29068826d5ebb67ac6d6d68 Author: Pierre-Emmanuel Patry Date: Tue Apr 1 16:08:37 2025 +0200 Remove unused error constructor and getter These constructor for eroneous state are not in use anymore since we replaced this error state with an optional in the parent nodes. gcc/rust/ChangeLog: * ast/rust-expr.h: Remove error getter and constructor. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/rust/ast/rust-expr.h | 5 - 1 file changed, 5 deletions(-) diff --git a/gcc/rust/ast/rust-expr.h b/gcc/rust/ast/rust-expr.h index 3ce78c643c73..e6cfa2709f93 100644 --- a/gcc/rust/ast/rust-expr.h +++ b/gcc/rust/ast/rust-expr.h @@ -31,11 +31,6 @@ public: {} // Returns whether the LoopLabel is in an error state. - bool is_error () const { return label.is_error (); } - - // Creates an error state LoopLabel. - static LoopLabel error () { return LoopLabel (Lifetime::error ()); } - location_t get_locus () const { return locus; } Lifetime &get_lifetime () { return label; }
[gcc/devel/rust/master] nr2.0: Remove duplicate self visit
https://gcc.gnu.org/g:ea91cee92d70de35def75cbae69eb4ac3189ee78 commit ea91cee92d70de35def75cbae69eb4ac3189ee78 Author: Owen Avery Date: Tue Apr 1 17:50:32 2025 -0400 nr2.0: Remove duplicate self visit gcc/rust/ChangeLog: * ast/rust-ast-visitor.cc (DefaultASTVisitor::visit): Remove explicit visitation of a function's self parameter, as if it exists it'll be visited as one of the function parameters. gcc/testsuite/ChangeLog: * rust/compile/nr2/exclude: Remove entry. Signed-off-by: Owen Avery Diff: --- gcc/rust/ast/rust-ast-visitor.cc | 2 -- gcc/testsuite/rust/compile/nr2/exclude | 1 - 2 files changed, 3 deletions(-) diff --git a/gcc/rust/ast/rust-ast-visitor.cc b/gcc/rust/ast/rust-ast-visitor.cc index 0d2dc00c2b27..2949f1cc81be 100644 --- a/gcc/rust/ast/rust-ast-visitor.cc +++ b/gcc/rust/ast/rust-ast-visitor.cc @@ -824,8 +824,6 @@ DefaultASTVisitor::visit (AST::Function &function) visit (function.get_qualifiers ()); for (auto &generic : function.get_generic_params ()) visit (generic); - if (function.has_self_param ()) -visit (function.get_self_param ()); for (auto ¶m : function.get_function_params ()) visit (param); if (function.has_return_type ()) diff --git a/gcc/testsuite/rust/compile/nr2/exclude b/gcc/testsuite/rust/compile/nr2/exclude index adc199e59e38..76ef39f982d3 100644 --- a/gcc/testsuite/rust/compile/nr2/exclude +++ b/gcc/testsuite/rust/compile/nr2/exclude @@ -1,7 +1,6 @@ canonical_paths1.rs cfg1.rs generics9.rs -issue-2043.rs issue-2812.rs issue-3315-2.rs lookup_err1.rs
[gcc/devel/rust/master] Change optional to expected for parse_loop_label
https://gcc.gnu.org/g:5ab8589e09ccaf7d36c9331425fba9413f40b26b commit 5ab8589e09ccaf7d36c9331425fba9413f40b26b Author: Pierre-Emmanuel Patry Date: Thu Apr 3 13:16:33 2025 +0200 Change optional to expected for parse_loop_label gcc/rust/ChangeLog: * parse/rust-parse-impl.h (Parser::parse_loop_label): Change function return type to expected. (Parser::parse_labelled_loop_expr): Adapt call location to new return type. * parse/rust-parse.h (enum class): Update function prototype. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/rust/parse/rust-parse-impl.h | 18 -- gcc/rust/parse/rust-parse.h | 8 +++- 2 files changed, 19 insertions(+), 7 deletions(-) diff --git a/gcc/rust/parse/rust-parse-impl.h b/gcc/rust/parse/rust-parse-impl.h index 32177c5ce2c0..073775eaf068 100644 --- a/gcc/rust/parse/rust-parse-impl.h +++ b/gcc/rust/parse/rust-parse-impl.h @@ -7568,14 +7568,15 @@ Parser::parse_continue_expr (AST::AttrVec outer_attrs, // Parses a loop label used in loop expressions. template -tl::optional +tl::expected Parser::parse_loop_label (const_TokenPtr tok) { // parse lifetime - if doesn't exist, assume no label if (tok->get_id () != LIFETIME) { // not necessarily an error - return tl::nullopt; + return tl::unexpected ( + ParseLoopLabelError::NOT_LOOP_LABEL); } /* FIXME: check for named lifetime requirement here? or check in semantic * analysis phase? */ @@ -7584,10 +7585,11 @@ Parser::parse_loop_label (const_TokenPtr tok) if (!skip_token (COLON)) { // skip somewhere? - return tl::nullopt; + return tl::unexpected ( + ParseLoopLabelError::MISSING_COLON); } - return tl::optional ( + return tl::expected ( AST::LoopLabel (std::move (label), tok->get_locus ())); } @@ -8217,8 +8219,8 @@ Parser::parse_labelled_loop_expr (const_TokenPtr tok, // parse loop label (required) // TODO: Convert this return type to tl::expected instead of tl::optional - tl::optional label = parse_loop_label (tok); - if (!label) + auto parsed_label = parse_loop_label (tok); + if (!parsed_label) { Error error (lexer.peek_token ()->get_locus (), "failed to parse loop label in labelled loop expr"); @@ -8228,6 +8230,10 @@ Parser::parse_labelled_loop_expr (const_TokenPtr tok, return nullptr; } + auto label = parsed_label +? tl::optional (parsed_label.value ()) +: tl::nullopt; + // branch on next token const_TokenPtr t = lexer.peek_token (); switch (t->get_id ()) diff --git a/gcc/rust/parse/rust-parse.h b/gcc/rust/parse/rust-parse.h index 5373106c1890..ff7987930fba 100644 --- a/gcc/rust/parse/rust-parse.h +++ b/gcc/rust/parse/rust-parse.h @@ -33,6 +33,11 @@ class ParseLifetimeParamError class ParseLifetimeError { }; +enum class ParseLoopLabelError +{ + NOT_LOOP_LABEL, + MISSING_COLON, +}; enum ParseSelfError { SELF_PTR, @@ -620,7 +625,8 @@ private: std::unique_ptr parse_labelled_loop_expr (const_TokenPtr tok, AST::AttrVec outer_attrs = AST::AttrVec ()); - tl::optional parse_loop_label (const_TokenPtr tok); + tl::expected + parse_loop_label (const_TokenPtr tok); std::unique_ptr parse_async_block_expr (AST::AttrVec outer_attrs = AST::AttrVec ()); std::unique_ptr parse_grouped_expr (AST::AttrVec outer_attrs
[gcc/devel/rust/master] Rename label getter in ContinueExpr
https://gcc.gnu.org/g:416e4b8449175e1862807f37d8c2bda554942ec8 commit 416e4b8449175e1862807f37d8c2bda554942ec8 Author: Pierre-Emmanuel Patry Date: Thu Apr 3 14:40:15 2025 +0200 Rename label getter in ContinueExpr gcc/rust/ChangeLog: * ast/rust-ast-collector.cc (TokenCollector::visit): Call unchecked getter. * ast/rust-ast-visitor.cc (DefaultASTVisitor::visit): Likewise. * ast/rust-ast.cc (ContinueExpr::as_string): Likewise. * hir/rust-ast-lower-expr.cc (ASTLoweringExpr::visit): Likewise. * resolve/rust-ast-resolve-expr.cc (ResolveExpr::visit): Likewise. * resolve/rust-late-name-resolver-2.0.cc (Late::visit): Likewise. * ast/rust-expr.h: Add new getter for the optional and rename getter to get_label_unchecked. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/rust/ast/rust-ast-collector.cc | 2 +- gcc/rust/ast/rust-ast-visitor.cc| 2 +- gcc/rust/ast/rust-ast.cc| 2 +- gcc/rust/ast/rust-expr.h| 7 +-- gcc/rust/hir/rust-ast-lower-expr.cc | 2 +- gcc/rust/resolve/rust-ast-resolve-expr.cc | 6 +++--- gcc/rust/resolve/rust-late-name-resolver-2.0.cc | 2 +- 7 files changed, 13 insertions(+), 10 deletions(-) diff --git a/gcc/rust/ast/rust-ast-collector.cc b/gcc/rust/ast/rust-ast-collector.cc index d0ecedb0c313..d81e51e89b66 100644 --- a/gcc/rust/ast/rust-ast-collector.cc +++ b/gcc/rust/ast/rust-ast-collector.cc @@ -1279,7 +1279,7 @@ TokenCollector::visit (ContinueExpr &expr) { push (Rust::Token::make (CONTINUE, expr.get_locus ())); if (expr.has_label ()) -visit (expr.get_label ()); +visit (expr.get_label_unchecked ()); } void diff --git a/gcc/rust/ast/rust-ast-visitor.cc b/gcc/rust/ast/rust-ast-visitor.cc index 87364a0b0f5b..21230113b7b5 100644 --- a/gcc/rust/ast/rust-ast-visitor.cc +++ b/gcc/rust/ast/rust-ast-visitor.cc @@ -478,7 +478,7 @@ DefaultASTVisitor::visit (AST::ContinueExpr &expr) { visit_outer_attrs (expr); if (expr.has_label ()) -visit (expr.get_label ()); +visit (expr.get_label_unchecked ()); } void diff --git a/gcc/rust/ast/rust-ast.cc b/gcc/rust/ast/rust-ast.cc index bba4b156b5f7..2311c579fd6c 100644 --- a/gcc/rust/ast/rust-ast.cc +++ b/gcc/rust/ast/rust-ast.cc @@ -1631,7 +1631,7 @@ ContinueExpr::as_string () const std::string str ("continue "); if (has_label ()) -str += get_label ().as_string (); +str += get_label_unchecked ().as_string (); return str; } diff --git a/gcc/rust/ast/rust-expr.h b/gcc/rust/ast/rust-expr.h index 70cb6d403551..4c832f9a06f4 100644 --- a/gcc/rust/ast/rust-expr.h +++ b/gcc/rust/ast/rust-expr.h @@ -2879,8 +2879,11 @@ public: outer_attrs = std::move (new_attrs); } - Lifetime &get_label () { return label.value (); } - const Lifetime &get_label () const { return label.value (); } + Lifetime &get_label_unchecked () { return label.value (); } + const Lifetime &get_label_unchecked () const { return label.value (); } + + tl::optional &get_label () { return label; } + const tl::optional &get_label () const { return label; } Expr::Kind get_expr_kind () const override { return Expr::Kind::Continue; } diff --git a/gcc/rust/hir/rust-ast-lower-expr.cc b/gcc/rust/hir/rust-ast-lower-expr.cc index 7bb732033cb7..2ee5591f1526 100644 --- a/gcc/rust/hir/rust-ast-lower-expr.cc +++ b/gcc/rust/hir/rust-ast-lower-expr.cc @@ -622,7 +622,7 @@ ASTLoweringExpr::visit (AST::ContinueExpr &expr) { tl::optional break_label; if (expr.has_label ()) -break_label = lower_lifetime (expr.get_label ()); +break_label = lower_lifetime (expr.get_label_unchecked ()); auto crate_num = mappings.get_current_crate (); Analysis::NodeMapping mapping (crate_num, expr.get_node_id (), diff --git a/gcc/rust/resolve/rust-ast-resolve-expr.cc b/gcc/rust/resolve/rust-ast-resolve-expr.cc index d83663810262..c0ce827606be 100644 --- a/gcc/rust/resolve/rust-ast-resolve-expr.cc +++ b/gcc/rust/resolve/rust-ast-resolve-expr.cc @@ -594,7 +594,7 @@ ResolveExpr::visit (AST::ContinueExpr &expr) { if (expr.has_label ()) { - auto label = expr.get_label (); + auto label = expr.get_label_unchecked (); if (label.get_lifetime_type () != AST::Lifetime::LifetimeType::NAMED) { rust_error_at (label.get_locus (), @@ -608,8 +608,8 @@ ResolveExpr::visit (AST::ContinueExpr &expr) label.get_lifetime_name ()), &resolved_node)) { - rust_error_at (expr.get_label ().get_locus (), ErrorCode::E0426, -"use of undeclared label %qs", + rust_error_at (expr.get_label_unchecked ().get_locus (), +ErrorCode::E0426, "use of undeclared label %qs", label.as_string ().c_str ()); return; } diff --git a/gcc/rust/re
[gcc/devel/rust/master] Resolve labels within break or continue expressions
https://gcc.gnu.org/g:429897c851b460b9256d96e3e504dfe15342d125 commit 429897c851b460b9256d96e3e504dfe15342d125 Author: Pierre-Emmanuel Patry Date: Wed Apr 2 17:41:54 2025 +0200 Resolve labels within break or continue expressions gcc/rust/ChangeLog: * resolve/rust-late-name-resolver-2.0.cc (Late::visit): Add call to label resolution if there is one label. (Late::resolve_label): Look for labels and emit an error message on failure. * resolve/rust-late-name-resolver-2.0.h: Add function prototypes. gcc/testsuite/ChangeLog: * rust/compile/nr2/exclude: Remove test. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/rust/resolve/rust-late-name-resolver-2.0.cc | 36 ++--- gcc/rust/resolve/rust-late-name-resolver-2.0.h | 3 +++ gcc/testsuite/rust/compile/nr2/exclude | 1 - 3 files changed, 29 insertions(+), 11 deletions(-) diff --git a/gcc/rust/resolve/rust-late-name-resolver-2.0.cc b/gcc/rust/resolve/rust-late-name-resolver-2.0.cc index 886a9fc8857a..717bf5c1184f 100644 --- a/gcc/rust/resolve/rust-late-name-resolver-2.0.cc +++ b/gcc/rust/resolve/rust-late-name-resolver-2.0.cc @@ -187,6 +187,9 @@ Late::visit (AST::SelfParam ¶m) void Late::visit (AST::BreakExpr &expr) { + if (expr.has_label ()) +resolve_label (expr.get_label ().get_lifetime ()); + if (expr.has_break_expr ()) { auto &break_expr = expr.get_break_expr (); @@ -215,20 +218,33 @@ Late::visit (AST::BreakExpr &expr) void Late::visit (AST::LoopLabel &label) { - // Shall we move this to visit(AST::Lifetime) or do we need to - // keep the context ? - auto lifetime = label.get_lifetime (); + auto &lifetime = label.get_lifetime (); + ctx.labels.insert (Identifier (lifetime.as_string (), lifetime.get_locus ()), +lifetime.get_node_id ()); +} + +void +Late::resolve_label (AST::Lifetime &lifetime) +{ if (auto resolved = ctx.labels.get (lifetime.as_string ())) { - ctx.map_usage (Usage (lifetime.get_node_id ()), -Definition (resolved->get_node_id ())); + if (resolved->get_node_id () != lifetime.get_node_id ()) + ctx.map_usage (Usage (lifetime.get_node_id ()), + Definition (resolved->get_node_id ())); } else -{ - ctx.labels.insert (Identifier (lifetime.as_string (), -lifetime.get_locus ()), -lifetime.get_node_id ()); -} +rust_error_at (lifetime.get_locus (), ErrorCode::E0426, + "use of undeclared label %qs", + lifetime.as_string ().c_str ()); +} + +void +Late::visit (AST::ContinueExpr &expr) +{ + if (expr.has_label ()) +resolve_label (expr.get_label ()); + + DefaultResolver::visit (expr); } void diff --git a/gcc/rust/resolve/rust-late-name-resolver-2.0.h b/gcc/rust/resolve/rust-late-name-resolver-2.0.h index 3f5097fae987..52079cc42c9e 100644 --- a/gcc/rust/resolve/rust-late-name-resolver-2.0.h +++ b/gcc/rust/resolve/rust-late-name-resolver-2.0.h @@ -48,6 +48,7 @@ public: void visit (AST::IdentifierExpr &) override; void visit (AST::StructExprFieldIdentifier &) override; void visit (AST::BreakExpr &) override; + void visit (AST::ContinueExpr &) override; void visit (AST::LoopLabel &) override; void visit (AST::PathInExpression &) override; void visit (AST::TypePath &) override; @@ -62,6 +63,8 @@ public: void visit (AST::ClosureExprInnerTyped &) override; private: + void resolve_label (AST::Lifetime &lifetime); + /* Setup Rust's builtin types (u8, i32, !...) in the resolver */ void setup_builtin_types (); diff --git a/gcc/testsuite/rust/compile/nr2/exclude b/gcc/testsuite/rust/compile/nr2/exclude index c688026a7b8f..665e0cf4d99b 100644 --- a/gcc/testsuite/rust/compile/nr2/exclude +++ b/gcc/testsuite/rust/compile/nr2/exclude @@ -12,7 +12,6 @@ privacy8.rs pub_restricted_1.rs pub_restricted_2.rs pub_restricted_3.rs -undeclared_label.rs use_1.rs issue-2905-2.rs derive_clone_enum3.rs
[gcc/devel/rust/master] nr2.0: Adjust test macro6.rs
https://gcc.gnu.org/g:d61c21976610a13fa255093dff10f9aa6e4b3040 commit d61c21976610a13fa255093dff10f9aa6e4b3040 Author: Owen Avery Date: Sun Mar 23 21:40:47 2025 -0400 nr2.0: Adjust test macro6.rs gcc/testsuite/ChangeLog: * rust/compile/macros/mbe/macro6.rs: Remove call of undefined function. * rust/compile/nr2/exclude: Remove macros/mbe/macro6.rs. Signed-off-by: Owen Avery Diff: --- gcc/testsuite/rust/compile/macros/mbe/macro6.rs | 2 +- gcc/testsuite/rust/compile/nr2/exclude | 1 - 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/gcc/testsuite/rust/compile/macros/mbe/macro6.rs b/gcc/testsuite/rust/compile/macros/mbe/macro6.rs index 9c54a674533d..bbaaa25eb52c 100644 --- a/gcc/testsuite/rust/compile/macros/mbe/macro6.rs +++ b/gcc/testsuite/rust/compile/macros/mbe/macro6.rs @@ -1,6 +1,6 @@ macro_rules! zero_or_one { ($($a:literal)?) => { -f(); +1 + 2; } } diff --git a/gcc/testsuite/rust/compile/nr2/exclude b/gcc/testsuite/rust/compile/nr2/exclude index 9502f3981912..4772517c47e4 100644 --- a/gcc/testsuite/rust/compile/nr2/exclude +++ b/gcc/testsuite/rust/compile/nr2/exclude @@ -3,7 +3,6 @@ cfg1.rs generics9.rs issue-3315-2.rs lookup_err1.rs -macros/mbe/macro6.rs multiple_bindings1.rs multiple_bindings2.rs privacy5.rs
[gcc r15-9287] gccrs: nr2.0: Improve test script
https://gcc.gnu.org/g:89ca1e3cb697a87f02682a1fb1f62f02d0671c57 commit r15-9287-g89ca1e3cb697a87f02682a1fb1f62f02d0671c57 Author: Owen Avery Date: Sun Mar 30 19:08:45 2025 -0400 gccrs: nr2.0: Improve test script gcc/testsuite/ChangeLog: * rust/compile/nr2/compile.exp: Avoid absolute paths in output, adjust phrasing of output, and avoid false XPASS output when tests are run in parallel. Signed-off-by: Owen Avery Diff: --- gcc/testsuite/rust/compile/nr2/compile.exp | 32 +- 1 file changed, 18 insertions(+), 14 deletions(-) diff --git a/gcc/testsuite/rust/compile/nr2/compile.exp b/gcc/testsuite/rust/compile/nr2/compile.exp index 35637f11ee8c..4d91dd004a3d 100644 --- a/gcc/testsuite/rust/compile/nr2/compile.exp +++ b/gcc/testsuite/rust/compile/nr2/compile.exp @@ -47,18 +47,22 @@ namespace eval rust-nr2-ns { set tests_expect_ok "" set tests_expect_err "" +set compile_dir [list {*}[file split $srcdir] {*}[file split $subdir]] +set compile_dir [lreplace $compile_dir end end] + foreach test_dir $test_dirs { -set directory [list {*}[file split $srcdir] {*}[file split $subdir]] - set directory [lreplace $directory end end] - set directory [list {*}$directory {*}$test_dir] -foreach test [lsort [glob -nocomplain -tails -directory [file join {*}$directory] *.rs]] { +foreach test [lsort [glob -nocomplain -tails -directory [file join {*}$compile_dir {*}$test_dir] *.rs]] { # use '/' as the path seperator for entries in the exclude file set test_lbl [join [list {*}$test_dir $test] "/"] set idx [lsearch -exact -sorted $exclude $test_lbl] if {$idx == -1} { - lappend tests_expect_ok [file join {*}$directory $test] + if {[runtest_file_p $runtests [file join {*}$compile_dir {*}$test_dir $test]]} { + lappend tests_expect_ok [list {*}$test_dir $test] + } } else { - lappend tests_expect_err [file join {*}$directory $test] + if {[runtest_file_p $runtests [file join {*}$compile_dir {*}$test_dir $test]]} { + lappend tests_expect_err [list {*}$test_dir $test] + } set exclude [lreplace $exclude $idx $idx] } } @@ -83,10 +87,10 @@ namespace eval rust-nr2-ns { variable record_test_out switch $type { FAIL { - lappend record_test_out "$type: $msg" + lappend record_test_out [list $type $msg] } XPASS { - lappend record_test_out "$type: $msg" + lappend record_test_out [list $type $msg] } } } @@ -109,23 +113,23 @@ namespace eval rust-nr2-ns { # check for unexpected failures foreach test $tests_expect_ok { -set fails [try_test $test] +set fails [try_test [file join {*}$compile_dir {*}$test]] if {[llength $fails] != 0} { foreach ent $fails { - record_test FAIL "$test: nr2 failure: $ent" + record_test [lindex $ent 0] "on nr2: [lindex $ent 1]" } } else { - record_test PASS "$test: nr2 success" + record_test PASS "[file join {*}$test] on nr2" } } #check for unexpected successes foreach test $tests_expect_err { -set fails [try_test $test] +set fails [try_test [file join {*}$compile_dir {*}$test]] if {[llength $fails] == 0} { - record_test XPASS "$test: nr2 unexpectedly passed" + record_test XPASS "[file join {*}$test] on nr2" } else { - record_test XFAIL "$test: nr2 was rightfully excluded" + record_test XFAIL "[file join {*}$test] on nr2 was rightfully excluded" } } }
[gcc r15-9293] gccrs: Make loop label truly optional
https://gcc.gnu.org/g:ff04ba261afe95ae7dc20099aab599de11480589 commit r15-9293-gff04ba261afe95ae7dc20099aab599de11480589 Author: Pierre-Emmanuel Patry Date: Tue Apr 1 15:57:47 2025 +0200 gccrs: Make loop label truly optional A loop label error state was in use to represent missing loop label but this may be easily forgotten and the optional nature of the label was misrepresented. gcc/rust/ChangeLog: * ast/rust-ast-builder.cc (Builder::block): Call with a nullopt instead of an error loop label. (WhileLetLoopExpr::as_string): Use getter function and adapt to newtype. * ast/rust-ast.cc (WhileLoopExpr::as_string): Likewise. (LoopExpr::as_string): Likewise. (BreakExpr::as_string): Likewise. (ForLoopExpr::as_string): Likewise. * ast/rust-expr.h (class BlockExpr): Make loop label optional. (class BreakExpr): Likewise. * expand/rust-derive-clone.cc (DeriveClone::clone_fn): Use nullopt. * expand/rust-derive-debug.cc (DeriveDebug::stub_debug_fn): Likewise. * expand/rust-derive-default.cc (DeriveDefault::default_fn): Likewise. * expand/rust-derive-eq.cc: Likewise. * parse/rust-parse-impl.h (Parser::parse_block_expr): Use optional for arguments. (Parser::parse_loop_expr): Likewise. (Parser::parse_while_loop_expr): Likewise. (Parser::parse_while_let_loop_expr): Likewise. (Parser::parse_for_loop_expr): Likewise. (Parser::parse_labelled_loop_expr): Likewise. (Parser::parse_loop_label): Return an optional. * parse/rust-parse.h: Update function prototype and use nullopt for default values. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/rust/ast/rust-ast-builder.cc | 6 +-- gcc/rust/ast/rust-ast.cc | 10 ++--- gcc/rust/ast/rust-expr.h | 35 --- gcc/rust/expand/rust-derive-clone.cc | 3 +- gcc/rust/expand/rust-derive-debug.cc | 3 +- gcc/rust/expand/rust-derive-default.cc | 3 +- gcc/rust/expand/rust-derive-eq.cc | 3 +- gcc/rust/parse/rust-parse-impl.h | 80 +- gcc/rust/parse/rust-parse.h| 12 ++--- 9 files changed, 77 insertions(+), 78 deletions(-) diff --git a/gcc/rust/ast/rust-ast-builder.cc b/gcc/rust/ast/rust-ast-builder.cc index cdc6eec254bc..5eea46933611 100644 --- a/gcc/rust/ast/rust-ast-builder.cc +++ b/gcc/rust/ast/rust-ast-builder.cc @@ -335,9 +335,9 @@ std::unique_ptr Builder::block (std::vector> &&stmts, std::unique_ptr &&tail_expr) const { - return std::unique_ptr ( -new BlockExpr (std::move (stmts), std::move (tail_expr), {}, {}, - LoopLabel::error (), loc, loc)); + return std::unique_ptr (new BlockExpr (std::move (stmts), + std::move (tail_expr), {}, + {}, tl::nullopt, loc, loc)); } std::unique_ptr diff --git a/gcc/rust/ast/rust-ast.cc b/gcc/rust/ast/rust-ast.cc index e4a1b369970e..c7e0397fca49 100644 --- a/gcc/rust/ast/rust-ast.cc +++ b/gcc/rust/ast/rust-ast.cc @@ -2095,7 +2095,7 @@ WhileLoopExpr::as_string () const if (!has_loop_label ()) str += "none"; else -str += loop_label.as_string (); +str += get_loop_label ().as_string (); str += "\n Conditional expr: " + condition->as_string (); @@ -2115,7 +2115,7 @@ WhileLetLoopExpr::as_string () const if (!has_loop_label ()) str += "none"; else -str += loop_label.as_string (); +str += get_loop_label ().as_string (); str += "\n Match arm patterns: "; if (match_arm_patterns.empty ()) @@ -2146,7 +2146,7 @@ LoopExpr::as_string () const if (!has_loop_label ()) str += "none"; else -str += loop_label.as_string (); +str += get_loop_label ().as_string (); str += "\n Loop block: " + loop_block->as_string (); @@ -2183,7 +2183,7 @@ BreakExpr::as_string () const std::string str ("break "); if (has_label ()) -str += label.as_string () + " "; +str += get_label ().as_string () + " "; if (has_break_expr ()) str += break_expr->as_string (); @@ -2545,7 +2545,7 @@ ForLoopExpr::as_string () const if (!has_loop_label ()) str += "none"; else -str += loop_label.as_string (); +str += get_loop_label ().as_string (); str += "\n Pattern: " + pattern->as_string (); diff --git a/gcc/rust/ast/rust-expr.h b/gcc/rust/ast/rust-expr.h index cff09fe17d7b..3ce78c643c73 100644 --- a/gcc/rust/ast/rust-expr.h +++ b/gcc/rust/ast/rust-expr.h @@ -2590,7 +2590,7 @@ class BlockExpr : public ExprWithBlock std::vector inner_attrs; std::vector > statements; std::unique_ptr expr; - LoopLabel label; + tl::optional label; location_t start_locus; location_t end_locus; bool m
[gcc r15-9275] gccrs: nr2.0: Handle global paths
https://gcc.gnu.org/g:0282fd7cabe365e639deb8848cf29fbd00470e63 commit r15-9275-g0282fd7cabe365e639deb8848cf29fbd00470e63 Author: Owen Avery Date: Mon Mar 24 22:49:12 2025 -0400 gccrs: nr2.0: Handle global paths gcc/rust/ChangeLog: * resolve/rust-forever-stack.h (ForeverStack::ForeverStack): Initialize extern_prelude. (ForeverStack::resolve_path): Add parameter has_opening_scope_resolution. (ForeverStack::extern_prelude): Add field. * resolve/rust-forever-stack.hxx: Include rust-edition.h. (ForeverStacl::resolve_path): Handle global paths (paths with an opening scope resolution operator). * resolve/rust-late-name-resolver-2.0.cc (Late::visit): Handle global paths. * resolve/rust-name-resolution-context.h (NameResolutionContext::resolve_path): Handle global paths. gcc/testsuite/ChangeLog: * rust/compile/nr2/exclude: Remove entries. Signed-off-by: Owen Avery Diff: --- gcc/rust/resolve/rust-forever-stack.h | 7 ++- gcc/rust/resolve/rust-forever-stack.hxx | 79 +++-- gcc/rust/resolve/rust-late-name-resolver-2.0.cc | 18 ++ gcc/rust/resolve/rust-name-resolution-context.h | 41 +++-- gcc/testsuite/rust/compile/nr2/exclude | 2 - 5 files changed, 96 insertions(+), 51 deletions(-) diff --git a/gcc/rust/resolve/rust-forever-stack.h b/gcc/rust/resolve/rust-forever-stack.h index f390e3889df8..cf0265140def 100644 --- a/gcc/rust/resolve/rust-forever-stack.h +++ b/gcc/rust/resolve/rust-forever-stack.h @@ -549,6 +549,7 @@ public: ForeverStack () : root (Node (Rib (Rib::Kind::Normal), UNKNOWN_NODEID)), lang_prelude (Node (Rib (Rib::Kind::Prelude), UNKNOWN_NODEID, root)), + extern_prelude (Node (Rib (Rib::Kind::Prelude), UNKNOWN_NODEID)), cursor_reference (root) { rust_assert (root.is_root ()); @@ -671,7 +672,7 @@ public: */ template tl::optional resolve_path ( -const std::vector &segments, +const std::vector &segments, bool has_opening_scope_resolution, std::function insert_segment_resolution); // FIXME: Documentation @@ -768,6 +769,10 @@ private: * resolution */ Node lang_prelude; + /* + * The extern prelude, used for resolving external crates + */ + Node extern_prelude; std::reference_wrapper cursor_reference; diff --git a/gcc/rust/resolve/rust-forever-stack.hxx b/gcc/rust/resolve/rust-forever-stack.hxx index 885f28206840..993e2d4fd2ab 100644 --- a/gcc/rust/resolve/rust-forever-stack.hxx +++ b/gcc/rust/resolve/rust-forever-stack.hxx @@ -20,6 +20,7 @@ #include "rust-ast.h" #include "rust-diagnostics.h" #include "rust-forever-stack.h" +#include "rust-edition.h" #include "rust-rib.h" #include "rust-unwrap-segment.h" #include "optional.h" @@ -618,11 +619,24 @@ template template tl::optional ForeverStack::resolve_path ( - const std::vector &segments, + const std::vector &segments, bool has_opening_scope_resolution, std::function insert_segment_resolution) { // TODO: What to do if segments.empty() ? + // handle paths with opening scopes + std::function cleanup_current = [] () {}; + if (has_opening_scope_resolution) +{ + Node *last_current = &cursor_reference.get (); + if (get_rust_edition () == Edition::E2015) + cursor_reference = root; + else + cursor_reference = extern_prelude; + cleanup_current + = [this, last_current] () { cursor_reference = *last_current; }; +} + // if there's only one segment, we just use `get` if (segments.size () == 1) { @@ -633,6 +647,7 @@ ForeverStack::resolve_path ( lang_item.value ()); insert_segment_resolution (seg, seg_id); + cleanup_current (); // TODO: does NonShadowable matter? return Rib::Definition::NonShadowable (seg_id); } @@ -646,40 +661,44 @@ ForeverStack::resolve_path ( if (res && !res->is_ambiguous ()) insert_segment_resolution (segments.back (), res->get_node_id ()); + cleanup_current (); return res; } std::reference_wrapper starting_point = cursor (); - return find_starting_point (segments, starting_point, - insert_segment_resolution) -.and_then ([this, &segments, &starting_point, &insert_segment_resolution] ( -typename std::vector::const_iterator iterator) { - return resolve_segments (starting_point.get (), segments, iterator, - insert_segment_resolution); -}) -.and_then ([this, &segments, &insert_segment_resolution] ( -Node final_node) -> tl::optional { - // leave resolution within impl blocks to type checker - if (final_node.rib.kind == Rib::Kind::TraitOrImpl) - return tl::nullopt; - - auto &seg = unwrap_type_segment (segment
[gcc r15-9283] gccrs: feature: Add min_specialization feature
https://gcc.gnu.org/g:c5f1d576a224a61fa4c924ab5bf5ed038d7fdbc9 commit r15-9283-gc5f1d576a224a61fa4c924ab5bf5ed038d7fdbc9 Author: Arthur Cohen Date: Tue Apr 1 17:45:00 2025 +0200 gccrs: feature: Add min_specialization feature gcc/rust/ChangeLog: * checks/errors/rust-feature.cc (Feature::create): Handle `#![feature(min_specialization)]`. * checks/errors/rust-feature.h: Likewise. Diff: --- gcc/rust/checks/errors/rust-feature.cc | 4 gcc/rust/checks/errors/rust-feature.h | 1 + 2 files changed, 5 insertions(+) diff --git a/gcc/rust/checks/errors/rust-feature.cc b/gcc/rust/checks/errors/rust-feature.cc index 25af46cbed81..441a1b288fdc 100644 --- a/gcc/rust/checks/errors/rust-feature.cc +++ b/gcc/rust/checks/errors/rust-feature.cc @@ -55,6 +55,9 @@ Feature::create (Feature::Name f) "1.11.0", 37854); case Feature::Name::PRELUDE_IMPORT: return Feature (f, Feature::State::ACTIVE, "prelude_import", "1.0.0"); +case Feature::Name::MIN_SPECIALIZATION: + return Feature (f, Feature::State::ACTIVE, "min_specialization", + "1.0.0" /* FIXME: What version here? */, 31844); case Feature::Name::AUTO_TRAITS: return Feature (f, Feature::State::ACTIVE, "optin_builtin_traits", "1.0.0", 13231); @@ -80,6 +83,7 @@ const std::map Feature::name_hash_map = { {"raw_ref_op", Feature::Name::RAW_REF_OP}, {"exclusive_range_pattern", Feature::Name::EXCLUSIVE_RANGE_PATTERN}, {"prelude_import", Feature::Name::PRELUDE_IMPORT}, + {"min_specialization", Feature::Name::MIN_SPECIALIZATION}, }; // namespace Rust tl::optional diff --git a/gcc/rust/checks/errors/rust-feature.h b/gcc/rust/checks/errors/rust-feature.h index 9edae6d62c30..e7cb0afc6895 100644 --- a/gcc/rust/checks/errors/rust-feature.h +++ b/gcc/rust/checks/errors/rust-feature.h @@ -51,6 +51,7 @@ public: RAW_REF_OP, EXCLUSIVE_RANGE_PATTERN, PRELUDE_IMPORT, +MIN_SPECIALIZATION, }; const std::string &as_string () { return m_name_str; }
[gcc r15-9300] gccrs: Change optional to expected for parse_loop_label
https://gcc.gnu.org/g:37908277b1caeaea1e7d110692082928776401ae commit r15-9300-g37908277b1caeaea1e7d110692082928776401ae Author: Pierre-Emmanuel Patry Date: Thu Apr 3 13:16:33 2025 +0200 gccrs: Change optional to expected for parse_loop_label gcc/rust/ChangeLog: * parse/rust-parse-impl.h (Parser::parse_loop_label): Change function return type to expected. (Parser::parse_labelled_loop_expr): Adapt call location to new return type. * parse/rust-parse.h (enum class): Update function prototype. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/rust/parse/rust-parse-impl.h | 18 -- gcc/rust/parse/rust-parse.h | 8 +++- 2 files changed, 19 insertions(+), 7 deletions(-) diff --git a/gcc/rust/parse/rust-parse-impl.h b/gcc/rust/parse/rust-parse-impl.h index 40ecb2ed4417..3bb758ef1d28 100644 --- a/gcc/rust/parse/rust-parse-impl.h +++ b/gcc/rust/parse/rust-parse-impl.h @@ -7568,14 +7568,15 @@ Parser::parse_continue_expr (AST::AttrVec outer_attrs, // Parses a loop label used in loop expressions. template -tl::optional +tl::expected Parser::parse_loop_label (const_TokenPtr tok) { // parse lifetime - if doesn't exist, assume no label if (tok->get_id () != LIFETIME) { // not necessarily an error - return tl::nullopt; + return tl::unexpected ( + ParseLoopLabelError::NOT_LOOP_LABEL); } /* FIXME: check for named lifetime requirement here? or check in semantic * analysis phase? */ @@ -7584,10 +7585,11 @@ Parser::parse_loop_label (const_TokenPtr tok) if (!skip_token (COLON)) { // skip somewhere? - return tl::nullopt; + return tl::unexpected ( + ParseLoopLabelError::MISSING_COLON); } - return tl::optional ( + return tl::expected ( AST::LoopLabel (std::move (label), tok->get_locus ())); } @@ -8217,8 +8219,8 @@ Parser::parse_labelled_loop_expr (const_TokenPtr tok, // parse loop label (required) // TODO: Convert this return type to tl::expected instead of tl::optional - tl::optional label = parse_loop_label (tok); - if (!label) + auto parsed_label = parse_loop_label (tok); + if (!parsed_label) { Error error (lexer.peek_token ()->get_locus (), "failed to parse loop label in labelled loop expr"); @@ -8228,6 +8230,10 @@ Parser::parse_labelled_loop_expr (const_TokenPtr tok, return nullptr; } + auto label = parsed_label +? tl::optional (parsed_label.value ()) +: tl::nullopt; + // branch on next token const_TokenPtr t = lexer.peek_token (); switch (t->get_id ()) diff --git a/gcc/rust/parse/rust-parse.h b/gcc/rust/parse/rust-parse.h index 5373106c1890..ff7987930fba 100644 --- a/gcc/rust/parse/rust-parse.h +++ b/gcc/rust/parse/rust-parse.h @@ -33,6 +33,11 @@ class ParseLifetimeParamError class ParseLifetimeError { }; +enum class ParseLoopLabelError +{ + NOT_LOOP_LABEL, + MISSING_COLON, +}; enum ParseSelfError { SELF_PTR, @@ -620,7 +625,8 @@ private: std::unique_ptr parse_labelled_loop_expr (const_TokenPtr tok, AST::AttrVec outer_attrs = AST::AttrVec ()); - tl::optional parse_loop_label (const_TokenPtr tok); + tl::expected + parse_loop_label (const_TokenPtr tok); std::unique_ptr parse_async_block_expr (AST::AttrVec outer_attrs = AST::AttrVec ()); std::unique_ptr parse_grouped_expr (AST::AttrVec outer_attrs
[gcc r15-9285] gccrs: Fix ICE for reserved lifetime name
https://gcc.gnu.org/g:381da0e21dac1579156de9d76d58610b104f5699 commit r15-9285-g381da0e21dac1579156de9d76d58610b104f5699 Author: Philip Herron Date: Thu Apr 3 16:32:36 2025 +0100 gccrs: Fix ICE for reserved lifetime name This is a reserved name so this changes the assertion to a diagnostic. Fixes Rust-GCC#3647 gcc/rust/ChangeLog: * typecheck/rust-typecheck-context.cc (TypeCheckContext::lookup_lifetime): emit error gcc/testsuite/ChangeLog: * rust/compile/issue-3647.rs: New test. Signed-off-by: Philip Herron Diff: --- gcc/rust/typecheck/rust-typecheck-context.cc | 11 ++- gcc/testsuite/rust/compile/issue-3647.rs | 7 +++ 2 files changed, 17 insertions(+), 1 deletion(-) diff --git a/gcc/rust/typecheck/rust-typecheck-context.cc b/gcc/rust/typecheck/rust-typecheck-context.cc index f02e48467317..9112b998f168 100644 --- a/gcc/rust/typecheck/rust-typecheck-context.cc +++ b/gcc/rust/typecheck/rust-typecheck-context.cc @@ -514,7 +514,16 @@ TypeCheckContext::lookup_lifetime (const HIR::Lifetime &lifetime) const { if (lifetime.get_lifetime_type () == AST::Lifetime::NAMED) { - rust_assert (lifetime.get_name () != "static"); + if (lifetime.get_name () == "static") + { + rich_location r (line_table, lifetime.get_locus ()); + r.add_fixit_insert_after (lifetime.get_locus (), + "static is a reserved lifetime name"); + rust_error_at (r, ErrorCode::E0262, +"invalid lifetime parameter name: %qs", +lifetime.get_name ().c_str ()); + return tl::nullopt; + } const auto name = lifetime.get_name (); auto it = lifetime_name_interner.find (name); if (it == lifetime_name_interner.end ()) diff --git a/gcc/testsuite/rust/compile/issue-3647.rs b/gcc/testsuite/rust/compile/issue-3647.rs new file mode 100644 index ..51d9478d7b1e --- /dev/null +++ b/gcc/testsuite/rust/compile/issue-3647.rs @@ -0,0 +1,7 @@ +#![allow(dead_code)] +type A = fn(); + +type B = for<'static> fn(); +// { dg-error "invalid lifetime parameter name: .static. .E0262." "" { target *-*-* } .-1 } + +pub fn main() {}
[gcc r15-9303] gccrs: fix ICE segfault with empty feature gate
https://gcc.gnu.org/g:a75a697ff0a5bafd23c468940943b80082088dba commit r15-9303-ga75a697ff0a5bafd23c468940943b80082088dba Author: Matty Kuhn Date: Fri Apr 4 18:09:41 2025 -0600 gccrs: fix ICE segfault with empty feature gate This patch fixes an issue where an empty feature gate would segfault, instead of reporting a syntax error to the user. gcc/rust/ChangeLog: * ast/rust-ast.h: (AST::Attribute): add empty_input function * checks/errors/rust-feature-gate.cc: (FeatureGate::visit): check for empty feature gate gcc/testsuite/ChangeLog: * rust/compile/feature.rs: add an invalid empty feature to produce an error Signed-off-by: Matty Kuhn Diff: --- gcc/rust/ast/rust-ast.h | 3 +++ gcc/rust/checks/errors/rust-feature-gate.cc | 7 +++ gcc/testsuite/rust/compile/feature.rs | 2 ++ 3 files changed, 12 insertions(+) diff --git a/gcc/rust/ast/rust-ast.h b/gcc/rust/ast/rust-ast.h index 1091ba0593e0..09e0fce4f190 100644 --- a/gcc/rust/ast/rust-ast.h +++ b/gcc/rust/ast/rust-ast.h @@ -657,6 +657,9 @@ public: // Returns whether the attribute is considered an "empty" attribute. bool is_empty () const { return attr_input == nullptr && path.is_empty (); } + // Returns whether the attribute has no input + bool empty_input () const { return !attr_input; } + location_t get_locus () const { return locus; } AttrInput &get_attr_input () const { return *attr_input; } diff --git a/gcc/rust/checks/errors/rust-feature-gate.cc b/gcc/rust/checks/errors/rust-feature-gate.cc index f3daa61f170b..44007f99e5cf 100644 --- a/gcc/rust/checks/errors/rust-feature-gate.cc +++ b/gcc/rust/checks/errors/rust-feature-gate.cc @@ -40,6 +40,13 @@ FeatureGate::visit (AST::Crate &crate) { if (attr.get_path ().as_string () == "feature") { + // check for empty feature, such as `#![feature], this is an error + if (attr.empty_input ()) + { + rust_error_at (attr.get_locus (), ErrorCode::E0556, +"malformed % attribute input"); + continue; + } const auto &attr_input = attr.get_attr_input (); auto type = attr_input.get_attr_input_type (); if (type == AST::AttrInput::AttrInputType::TOKEN_TREE) diff --git a/gcc/testsuite/rust/compile/feature.rs b/gcc/testsuite/rust/compile/feature.rs index f743f9229b68..6f428f075a1b 100644 --- a/gcc/testsuite/rust/compile/feature.rs +++ b/gcc/testsuite/rust/compile/feature.rs @@ -2,5 +2,7 @@ #![feature(AA)] //{ dg-error "unknown feature .AA." } #![feature(iamcrabby)] // { dg-error "unknown feature .iamcrabby." } #![feature(nonexistent_gccrs_feature)] // { dg-error "unknown feature .nonexistent_gccrs_feature." } +// ErrorCode - E0556 +#![feature] // { dg-error "malformed .feature. attribute input" } fn main() {}
[gcc r15-9276] gccrs: Fix ICE when doing shift checks on const decl
https://gcc.gnu.org/g:e873e2a0b15871fb0bcdb07155fc9a7407f66286 commit r15-9276-ge873e2a0b15871fb0bcdb07155fc9a7407f66286 Author: Philip Herron Date: Mon Mar 31 17:58:24 2025 +0100 gccrs: Fix ICE when doing shift checks on const decl Const decls are just delcarations wrapping the value into the DECL_INITIAL and the shift checks we have assume no decls are involved and its just flat values. This patch simply unwraps the constant values if they exist. Fixes Rust-GCC#3665 gcc/rust/ChangeLog: * rust-gcc.cc (arithmetic_or_logical_expression): unwrap const decls gcc/testsuite/ChangeLog: * rust/compile/issue-3665.rs: New test. Signed-off-by: Philip Herron Diff: --- gcc/rust/rust-gcc.cc | 6 ++ gcc/testsuite/rust/compile/issue-3665.rs | 6 ++ 2 files changed, 12 insertions(+) diff --git a/gcc/rust/rust-gcc.cc b/gcc/rust/rust-gcc.cc index a6e8ea904a8a..72aef08e35a0 100644 --- a/gcc/rust/rust-gcc.cc +++ b/gcc/rust/rust-gcc.cc @@ -1074,6 +1074,12 @@ arithmetic_or_logical_expression (ArithmeticOrLogicalOperator op, tree left, if (left == error_mark_node || right == error_mark_node) return error_mark_node; + // unwrap the const decls if set + if (TREE_CODE (left) == CONST_DECL) +left = DECL_INITIAL (left); + if (TREE_CODE (right) == CONST_DECL) +right = DECL_INITIAL (right); + /* We need to determine if we're doing floating point arithmetics of integer arithmetics. */ bool floating_point = is_floating_point (left); diff --git a/gcc/testsuite/rust/compile/issue-3665.rs b/gcc/testsuite/rust/compile/issue-3665.rs new file mode 100644 index ..d66a81fc1aec --- /dev/null +++ b/gcc/testsuite/rust/compile/issue-3665.rs @@ -0,0 +1,6 @@ +pub const uint_val: usize = 1; +pub const uint_expr: usize = 1 << uint_val; + +pub fn test() -> usize { +uint_expr +}
[gcc r15-9280] gccrs: Fix ICE on invalid match arms
https://gcc.gnu.org/g:0f37641978a2ef2b7a50d230a16637a3cfd46c2d commit r15-9280-g0f37641978a2ef2b7a50d230a16637a3cfd46c2d Author: Philip Herron Date: Thu Apr 3 15:37:40 2025 +0100 gccrs: Fix ICE on invalid match arms We hit assertions on empty enum or unknown variant, this catches the error and emits a new diagnostic. Fixes Rust-GCC#3656 gcc/rust/ChangeLog: * typecheck/rust-hir-type-check-pattern.cc (TypeCheckPattern::visit): emit error gcc/testsuite/ChangeLog: * rust/compile/issue-3656.rs: New test. Signed-off-by: Philip Herron Diff: --- gcc/rust/typecheck/rust-hir-type-check-pattern.cc | 21 +++-- gcc/testsuite/rust/compile/issue-3656.rs | 10 ++ 2 files changed, 29 insertions(+), 2 deletions(-) diff --git a/gcc/rust/typecheck/rust-hir-type-check-pattern.cc b/gcc/rust/typecheck/rust-hir-type-check-pattern.cc index 3f9557a5c3e1..bd13f7a56185 100644 --- a/gcc/rust/typecheck/rust-hir-type-check-pattern.cc +++ b/gcc/rust/typecheck/rust-hir-type-check-pattern.cc @@ -277,7 +277,15 @@ TypeCheckPattern::visit (HIR::StructPattern &pattern) infered = pattern_ty; TyTy::ADTType *adt = static_cast (infered); - rust_assert (adt->number_of_variants () > 0); + if (adt->number_of_variants () == 0) +{ + HIR::PathInExpression &path = pattern.get_path (); + const AST::SimplePath &sp = path.as_simple_path (); + rust_error_at (pattern.get_locus (), ErrorCode::E0574, +"expected struct, variant or union type, found enum %qs", +sp.as_string ().c_str ()); + return; +} TyTy::VariantDef *variant = adt->get_variants ().at (0); if (adt->is_enum ()) @@ -285,7 +293,16 @@ TypeCheckPattern::visit (HIR::StructPattern &pattern) HirId variant_id = UNKNOWN_HIRID; bool ok = context->lookup_variant_definition ( pattern.get_path ().get_mappings ().get_hirid (), &variant_id); - rust_assert (ok); + if (!ok) + { + HIR::PathInExpression &path = pattern.get_path (); + const AST::SimplePath &sp = path.as_simple_path (); + rust_error_at ( + pattern.get_locus (), ErrorCode::E0574, + "expected struct, variant or union type, found enum %qs", + sp.as_string ().c_str ()); + return; + } ok = adt->lookup_variant_by_id (variant_id, &variant); rust_assert (ok); diff --git a/gcc/testsuite/rust/compile/issue-3656.rs b/gcc/testsuite/rust/compile/issue-3656.rs new file mode 100644 index ..e0bec2fa4a69 --- /dev/null +++ b/gcc/testsuite/rust/compile/issue-3656.rs @@ -0,0 +1,10 @@ +enum Foo { +Bar(isize), +} + +fn main() { +match Foo::Bar(205) { +Foo { i } => (), +// { dg-error "expected struct, variant or union type, found enum .Foo. .E0574." "" { target *-*-* } .-1 } +} +}
[gcc r15-9291] gccrs: Add check for label
https://gcc.gnu.org/g:d85a88aa3fdf2a5d66288d5809da864b956cc8d4 commit r15-9291-gd85a88aa3fdf2a5d66288d5809da864b956cc8d4 Author: Pierre-Emmanuel Patry Date: Mon Mar 31 17:01:18 2025 +0200 gccrs: Add check for label gcc/rust/ChangeLog: * ast/rust-ast-visitor.cc (DefaultASTVisitor::visit): Visit loop label only if it exists. gcc/testsuite/ChangeLog: * rust/compile/nr2/exclude: Remove passing test. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/rust/ast/rust-ast-visitor.cc | 3 ++- gcc/testsuite/rust/compile/nr2/exclude | 2 -- 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/gcc/rust/ast/rust-ast-visitor.cc b/gcc/rust/ast/rust-ast-visitor.cc index 9a8c24f17d84..6a81fa10aabd 100644 --- a/gcc/rust/ast/rust-ast-visitor.cc +++ b/gcc/rust/ast/rust-ast-visitor.cc @@ -568,7 +568,8 @@ DefaultASTVisitor::visit (AST::WhileLoopExpr &expr) { visit_outer_attrs (expr); visit (expr.get_predicate_expr ()); - visit (expr.get_loop_label ()); + if (expr.has_loop_label ()) +visit (expr.get_loop_label ()); visit (expr.get_loop_block ()); } diff --git a/gcc/testsuite/rust/compile/nr2/exclude b/gcc/testsuite/rust/compile/nr2/exclude index 76ef39f982d3..2f4585cbe8c4 100644 --- a/gcc/testsuite/rust/compile/nr2/exclude +++ b/gcc/testsuite/rust/compile/nr2/exclude @@ -23,8 +23,6 @@ derive-default1.rs derive-eq-invalid.rs derive-hash1.rs torture/alt_patterns1.rs -torture/loop4.rs -torture/loop8.rs torture/name_resolve1.rs issue-3568.rs issue-3663.rs
[gcc r15-9289] gccrs: Revert part of 44ffe1193269
https://gcc.gnu.org/g:d307dddfc1a7dd406e488b08a390ae5908542b1a commit r15-9289-gd307dddfc1a7dd406e488b08a390ae5908542b1a Author: Pierre-Emmanuel Patry Date: Thu Apr 3 17:27:46 2025 +0200 gccrs: Revert part of 44ffe1193269 This commit got rid of msvc specific code and remove the else clause, this triggered warning with tl::expected::value function. gcc/rust/ChangeLog: * util/expected.h: Use gcc_unreachable within gcc context. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/rust/util/expected.h | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/gcc/rust/util/expected.h b/gcc/rust/util/expected.h index a9e3bc2b2338..07ba8776214e 100644 --- a/gcc/rust/util/expected.h +++ b/gcc/rust/util/expected.h @@ -212,10 +212,8 @@ template throw std::forward(e); #else (void)e; -#ifdef _MSC_VER gcc_unreachable(); #endif -#endif } #ifndef TL_TRAITS_MUTEX @@ -2437,4 +2435,4 @@ void swap(expected &lhs, } } // namespace tl -#endif \ No newline at end of file +#endif
[gcc r15-9295] gccrs: Update ast visitor with proper check for looplabel
https://gcc.gnu.org/g:3cf4d5cb996a062a22fe6fb496a622ec7519bd65 commit r15-9295-g3cf4d5cb996a062a22fe6fb496a622ec7519bd65 Author: Pierre-Emmanuel Patry Date: Tue Apr 1 16:10:38 2025 +0200 gccrs: Update ast visitor with proper check for looplabel The visitor was visiting loop label even when they did not exist. gcc/rust/ChangeLog: * ast/rust-ast-visitor.cc (DefaultASTVisitor::visit): Add check for loop label before visiting it. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/rust/ast/rust-ast-visitor.cc | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/gcc/rust/ast/rust-ast-visitor.cc b/gcc/rust/ast/rust-ast-visitor.cc index 73c6b1ee31e1..38617bf4a99b 100644 --- a/gcc/rust/ast/rust-ast-visitor.cc +++ b/gcc/rust/ast/rust-ast-visitor.cc @@ -559,7 +559,8 @@ void DefaultASTVisitor::visit (AST::LoopExpr &expr) { visit_outer_attrs (expr); - visit (expr.get_loop_label ()); + if (expr.has_loop_label ()) +visit (expr.get_loop_label ()); visit (expr.get_loop_block ()); }
[gcc r15-9281] gccrs: Fix ICE on raw reference
https://gcc.gnu.org/g:f7fc904335edd53f428d76cd85a7bf3f8b55b2fe commit r15-9281-gf7fc904335edd53f428d76cd85a7bf3f8b55b2fe Author: Philip Herron Date: Thu Apr 3 15:39:58 2025 +0100 gccrs: Fix ICE on raw reference This patch adds support for raw references which enforce the pointer type away from a reference type. Fixes Rust-GCC#3667 gcc/rust/ChangeLog: * backend/rust-compile-base.cc (HIRCompileBase::address_expression): allow optional type * backend/rust-compile-base.h: update prototype * backend/rust-compile-expr.cc (CompileExpr::visit): update borrow expr * backend/rust-compile-extern.h: remove unused debug * backend/rust-compile-resolve-path.cc (HIRCompileBase::query_compile): update usage * hir/rust-ast-lower-expr.cc (ASTLoweringExpr::visit): lower raw ref * hir/tree/rust-hir-expr.cc (BorrowExpr::BorrowExpr): add flag for raw ref * hir/tree/rust-hir-expr.h (class BorrowExpr): add new raw ref field * typecheck/rust-hir-type-check-expr.cc (TypeCheckExpr::visit): add handle for raw ref gcc/testsuite/ChangeLog: * rust/compile/issue-3667.rs: New test. Signed-off-by: Philip Herron Diff: --- gcc/rust/backend/rust-compile-base.cc | 7 +-- gcc/rust/backend/rust-compile-base.h | 3 ++- gcc/rust/backend/rust-compile-expr.cc | 3 ++- gcc/rust/backend/rust-compile-extern.h | 6 -- gcc/rust/backend/rust-compile-resolve-path.cc | 4 ++-- gcc/rust/hir/rust-ast-lower-expr.cc| 11 --- gcc/rust/hir/tree/rust-hir-expr.cc | 4 ++-- gcc/rust/hir/tree/rust-hir-expr.h | 4 +++- gcc/rust/typecheck/rust-hir-type-check-expr.cc | 9 + gcc/testsuite/rust/compile/issue-3667.rs | 24 10 files changed, 53 insertions(+), 22 deletions(-) diff --git a/gcc/rust/backend/rust-compile-base.cc b/gcc/rust/backend/rust-compile-base.cc index b6bee8f9c2f1..0647718c841c 100644 --- a/gcc/rust/backend/rust-compile-base.cc +++ b/gcc/rust/backend/rust-compile-base.cc @@ -549,7 +549,7 @@ HIRCompileBase::mark_addressable (tree exp, location_t locus) } tree -HIRCompileBase::address_expression (tree expr, location_t location) +HIRCompileBase::address_expression (tree expr, location_t location, tree ptrty) { if (expr == error_mark_node) return error_mark_node; @@ -557,7 +557,10 @@ HIRCompileBase::address_expression (tree expr, location_t location) if (!mark_addressable (expr, location)) return error_mark_node; - return build_fold_addr_expr_loc (location, expr); + if (ptrty == NULL || ptrty == error_mark_node) +ptrty = build_pointer_type (TREE_TYPE (expr)); + + return build_fold_addr_expr_with_type_loc (location, expr, ptrty); } tree diff --git a/gcc/rust/backend/rust-compile-base.h b/gcc/rust/backend/rust-compile-base.h index 64c8106d1c28..467bfd0a4f73 100644 --- a/gcc/rust/backend/rust-compile-base.h +++ b/gcc/rust/backend/rust-compile-base.h @@ -29,7 +29,8 @@ class HIRCompileBase public: virtual ~HIRCompileBase () {} - static tree address_expression (tree expr, location_t locus); + static tree address_expression (tree expr, location_t locus, + tree ptrty = NULL_TREE); static tree compile_constant_expr ( Context *ctx, HirId coercion_id, TyTy::BaseType *resolved_type, diff --git a/gcc/rust/backend/rust-compile-expr.cc b/gcc/rust/backend/rust-compile-expr.cc index e4ab9f010b8e..37856a77f2c7 100644 --- a/gcc/rust/backend/rust-compile-expr.cc +++ b/gcc/rust/backend/rust-compile-expr.cc @@ -905,7 +905,8 @@ CompileExpr::visit (HIR::BorrowExpr &expr) &tyty)) return; - translated = address_expression (main_expr, expr.get_locus ()); + tree expected_type = TyTyResolveCompile::compile (ctx, tyty); + translated = address_expression (main_expr, expr.get_locus (), expected_type); } void diff --git a/gcc/rust/backend/rust-compile-extern.h b/gcc/rust/backend/rust-compile-extern.h index bacd1c044ec5..d6aa5899f624 100644 --- a/gcc/rust/backend/rust-compile-extern.h +++ b/gcc/rust/backend/rust-compile-extern.h @@ -34,16 +34,10 @@ class CompileExternItem : public HIRCompileBase, public: static tree compile (HIR::ExternalItem *item, Context *ctx, TyTy::BaseType *concrete = nullptr, - bool is_query_mode = false, location_t ref_locus = UNDEF_LOCATION) { CompileExternItem compiler (ctx, concrete, ref_locus); item->accept_vis (compiler); - -if (is_query_mode && compiler.reference == error_mark_node) - rust_internal_error_at (ref_locus, "failed to compile extern item: %s", - item->as_string ().c_str ()); - return compiler.reference; } diff --git a/gcc/rust/backend/rust-compile-resolve
[gcc r15-9297] gccrs: Fix unresolved label error message
https://gcc.gnu.org/g:8c51fd896d02cf515c8919b1a4be52739434060b commit r15-9297-g8c51fd896d02cf515c8919b1a4be52739434060b Author: Pierre-Emmanuel Patry Date: Wed Apr 2 17:38:28 2025 +0200 gccrs: Fix unresolved label error message gcc/rust/ChangeLog: * resolve/rust-ast-resolve-expr.cc (ResolveExpr::visit): Change error message to match rustc. gcc/testsuite/ChangeLog: * rust/compile/undeclared_label.rs: Change test expected string. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/rust/resolve/rust-ast-resolve-expr.cc | 8 gcc/testsuite/rust/compile/undeclared_label.rs | 4 ++-- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/gcc/rust/resolve/rust-ast-resolve-expr.cc b/gcc/rust/resolve/rust-ast-resolve-expr.cc index dc7f76d652dd..4bfd1b3ca4fe 100644 --- a/gcc/rust/resolve/rust-ast-resolve-expr.cc +++ b/gcc/rust/resolve/rust-ast-resolve-expr.cc @@ -486,8 +486,8 @@ ResolveExpr::visit (AST::BreakExpr &expr) &resolved_node)) { rust_error_at (label.get_locus (), ErrorCode::E0426, -"use of undeclared label %qs in %", -label.get_lifetime_name ().c_str ()); +"use of undeclared label %qs", +label.as_string ().c_str ()); return; } resolver->insert_resolved_label (label.get_node_id (), resolved_node); @@ -609,8 +609,8 @@ ResolveExpr::visit (AST::ContinueExpr &expr) &resolved_node)) { rust_error_at (expr.get_label ().get_locus (), ErrorCode::E0426, -"use of undeclared label %qs in %", -label.get_lifetime_name ().c_str ()); +"use of undeclared label %qs", +label.as_string ().c_str ()); return; } resolver->insert_resolved_label (label.get_node_id (), resolved_node); diff --git a/gcc/testsuite/rust/compile/undeclared_label.rs b/gcc/testsuite/rust/compile/undeclared_label.rs index 6efa2d98dbfb..9aa0553f6572 100644 --- a/gcc/testsuite/rust/compile/undeclared_label.rs +++ b/gcc/testsuite/rust/compile/undeclared_label.rs @@ -2,12 +2,12 @@ #![allow(unused)] fn resolve_label_continue() -> () { loop { -continue 'a; // { dg-error "use of undeclared label .a. in .continue." } +continue 'a; // { dg-error "use of undeclared label .'a." } } } fn resolve_label_break() -> () { loop { -break 'crabby; // { dg-error "use of undeclared label .crabby. in .break." } +break 'crabby; // { dg-error "use of undeclared label .'crabby." } } } fn main() {
[gcc r15-9304] gccrs: nr2.0: Adjust test issue-2812.rs
https://gcc.gnu.org/g:df45e75724f064b431a0dceb26a4f7320ef7018b commit r15-9304-gdf45e75724f064b431a0dceb26a4f7320ef7018b Author: Owen Avery Date: Mon Mar 24 18:27:41 2025 -0400 gccrs: nr2.0: Adjust test issue-2812.rs gcc/testsuite/ChangeLog: * rust/compile/issue-2812.rs: Avoid multiple definition error. * rust/compile/nr2/exclude: Remove issue-2812.rs. Signed-off-by: Owen Avery Diff: --- gcc/testsuite/rust/compile/issue-2812.rs | 4 ++-- gcc/testsuite/rust/compile/nr2/exclude | 1 - 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/gcc/testsuite/rust/compile/issue-2812.rs b/gcc/testsuite/rust/compile/issue-2812.rs index 173259b12914..0de1738309f1 100644 --- a/gcc/testsuite/rust/compile/issue-2812.rs +++ b/gcc/testsuite/rust/compile/issue-2812.rs @@ -1,4 +1,4 @@ // { dg-additional-options "-frust-compile-until=astvalidation" } fn foo_1(&self); -fn foo_1(&mut self); -fn foo_1(self); +fn foo_2(&mut self); +fn foo_3(self); diff --git a/gcc/testsuite/rust/compile/nr2/exclude b/gcc/testsuite/rust/compile/nr2/exclude index 665e0cf4d99b..9502f3981912 100644 --- a/gcc/testsuite/rust/compile/nr2/exclude +++ b/gcc/testsuite/rust/compile/nr2/exclude @@ -1,7 +1,6 @@ canonical_paths1.rs cfg1.rs generics9.rs -issue-2812.rs issue-3315-2.rs lookup_err1.rs macros/mbe/macro6.rs
[gcc r15-9288] gccrs: refactoring rust_error_at "redefined multiple times"
https://gcc.gnu.org/g:72a0fb9d9897347e938f560aaf5f99e95838d5bd commit r15-9288-g72a0fb9d9897347e938f560aaf5f99e95838d5bd Author: Sri Ganesh Thota Date: Tue Mar 25 18:30:58 2025 +0530 gccrs: refactoring rust_error_at "redefined multiple times" gcc/rust/ChangeLog: * resolve/rust-ast-resolve-base.h (redefined_error): created a function for rust_error_at for redefined at multiple times. * resolve/rust-ast-resolve-implitem.h: changed rust_error_at to redefined_error. * resolve/rust-ast-resolve-stmt.cc (ResolveStmt::visit): changed rust_error_at to redefined_error. * resolve/rust-ast-resolve-stmt.h: changed rust_error_at to redefined_error. * resolve/rust-ast-resolve-toplevel.h: changed rust_error_at to redefined_error. Signed-off-by: Sri Ganesh Thota Diff: --- gcc/rust/resolve/rust-ast-resolve-base.h | 5 + gcc/rust/resolve/rust-ast-resolve-implitem.h | 19 - gcc/rust/resolve/rust-ast-resolve-stmt.cc| 2 +- gcc/rust/resolve/rust-ast-resolve-stmt.h | 20 - gcc/rust/resolve/rust-ast-resolve-toplevel.h | 32 ++-- 5 files changed, 41 insertions(+), 37 deletions(-) diff --git a/gcc/rust/resolve/rust-ast-resolve-base.h b/gcc/rust/resolve/rust-ast-resolve-base.h index 0d497f81eacc..ab74e84f0797 100644 --- a/gcc/rust/resolve/rust-ast-resolve-base.h +++ b/gcc/rust/resolve/rust-ast-resolve-base.h @@ -27,6 +27,11 @@ namespace Rust { namespace Resolver { +inline void +redefined_error (const rich_location &loc) +{ + rust_error_at (loc, "redefined multiple times"); +} class ResolverBase : public AST::ASTVisitor { diff --git a/gcc/rust/resolve/rust-ast-resolve-implitem.h b/gcc/rust/resolve/rust-ast-resolve-implitem.h index 971bf8faee2e..2081697fe8f8 100644 --- a/gcc/rust/resolve/rust-ast-resolve-implitem.h +++ b/gcc/rust/resolve/rust-ast-resolve-implitem.h @@ -51,7 +51,7 @@ public: [&] (const CanonicalPath &, NodeId, location_t locus) -> void { rich_location r (line_table, type.get_locus ()); r.add_range (locus); - rust_error_at (r, "defined multiple times"); + redefined_error (r); }); } @@ -67,7 +67,7 @@ public: [&] (const CanonicalPath &, NodeId, location_t locus) -> void { rich_location r (line_table, constant.get_locus ()); r.add_range (locus); - rust_error_at (r, "defined multiple times"); + redefined_error (r); }); } @@ -84,7 +84,7 @@ public: [&] (const CanonicalPath &, NodeId, location_t locus) -> void { rich_location r (line_table, function.get_locus ()); r.add_range (locus); - rust_error_at (r, "defined multiple times"); + redefined_error (r); }); } @@ -124,7 +124,7 @@ public: [&] (const CanonicalPath &, NodeId, location_t locus) -> void { rich_location r (line_table, function.get_locus ()); r.add_range (locus); - rust_error_at (r, "defined multiple times"); + redefined_error (r); }); mappings.insert_canonical_path (function.get_node_id (), cpath); @@ -144,7 +144,7 @@ public: [&] (const CanonicalPath &, NodeId, location_t locus) -> void { rich_location r (line_table, constant.get_locus ()); r.add_range (locus); - rust_error_at (r, "defined multiple times"); + redefined_error (r); }); mappings.insert_canonical_path (constant.get_node_id (), cpath); @@ -162,7 +162,7 @@ public: [&] (const CanonicalPath &, NodeId, location_t locus) -> void { rich_location r (line_table, type.get_locus ()); r.add_range (locus); - rust_error_at (r, "defined multiple times"); + redefined_error (r); }); mappings.insert_canonical_path (type.get_node_id (), cpath); @@ -202,7 +202,7 @@ public: [&] (const CanonicalPath &, NodeId, location_t locus) -> void { rich_location r (line_table, function.get_locus ()); r.add_range (locus); - rust_error_at (r, "defined multiple times"); + redefined_error (r); }); NodeId current_module = resolver->peek_current_module_scope (); @@ -221,7 +221,7 @@ public: [&] (const CanonicalPath &, NodeId, location_t locus) -> void { rich_location r (line_table, item.get_locus ()); r.add_range (locus); - rust_error_at (r, "defined multiple times"); + redefined_error (r); }); NodeId current_module = resolver->peek_current_module_scope (); @@ -239,8 +239,7 @@ public: [&] (const CanonicalPath &, NodeId, location_t locus) -> void { rich_location r (line_table, type.get_locus ()); r.add_range (locus); - - rust_error_at (r, "defined multiple times"); + redefined_error (r); }); NodeId current_module = resolver->peek_current_module_scope (); diff --git a/gcc/rust/resolve/rust-ast-resolve-stmt.cc b/
[gcc r15-9298] gccrs: Resolve labels within break or continue expressions
https://gcc.gnu.org/g:fb890cd43bc158af37fea846c423e069a90a9436 commit r15-9298-gfb890cd43bc158af37fea846c423e069a90a9436 Author: Pierre-Emmanuel Patry Date: Wed Apr 2 17:41:54 2025 +0200 gccrs: Resolve labels within break or continue expressions gcc/rust/ChangeLog: * resolve/rust-late-name-resolver-2.0.cc (Late::visit): Add call to label resolution if there is one label. (Late::resolve_label): Look for labels and emit an error message on failure. * resolve/rust-late-name-resolver-2.0.h: Add function prototypes. gcc/testsuite/ChangeLog: * rust/compile/nr2/exclude: Remove test. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/rust/resolve/rust-late-name-resolver-2.0.cc | 36 ++--- gcc/rust/resolve/rust-late-name-resolver-2.0.h | 3 +++ gcc/testsuite/rust/compile/nr2/exclude | 1 - 3 files changed, 29 insertions(+), 11 deletions(-) diff --git a/gcc/rust/resolve/rust-late-name-resolver-2.0.cc b/gcc/rust/resolve/rust-late-name-resolver-2.0.cc index e0006fdea279..3e69d3436733 100644 --- a/gcc/rust/resolve/rust-late-name-resolver-2.0.cc +++ b/gcc/rust/resolve/rust-late-name-resolver-2.0.cc @@ -187,6 +187,9 @@ Late::visit (AST::SelfParam ¶m) void Late::visit (AST::BreakExpr &expr) { + if (expr.has_label ()) +resolve_label (expr.get_label ().get_lifetime ()); + if (expr.has_break_expr ()) { auto &break_expr = expr.get_break_expr (); @@ -215,20 +218,33 @@ Late::visit (AST::BreakExpr &expr) void Late::visit (AST::LoopLabel &label) { - // Shall we move this to visit(AST::Lifetime) or do we need to - // keep the context ? - auto lifetime = label.get_lifetime (); + auto &lifetime = label.get_lifetime (); + ctx.labels.insert (Identifier (lifetime.as_string (), lifetime.get_locus ()), +lifetime.get_node_id ()); +} + +void +Late::resolve_label (AST::Lifetime &lifetime) +{ if (auto resolved = ctx.labels.get (lifetime.as_string ())) { - ctx.map_usage (Usage (lifetime.get_node_id ()), -Definition (resolved->get_node_id ())); + if (resolved->get_node_id () != lifetime.get_node_id ()) + ctx.map_usage (Usage (lifetime.get_node_id ()), + Definition (resolved->get_node_id ())); } else -{ - ctx.labels.insert (Identifier (lifetime.as_string (), -lifetime.get_locus ()), -lifetime.get_node_id ()); -} +rust_error_at (lifetime.get_locus (), ErrorCode::E0426, + "use of undeclared label %qs", + lifetime.as_string ().c_str ()); +} + +void +Late::visit (AST::ContinueExpr &expr) +{ + if (expr.has_label ()) +resolve_label (expr.get_label ()); + + DefaultResolver::visit (expr); } void diff --git a/gcc/rust/resolve/rust-late-name-resolver-2.0.h b/gcc/rust/resolve/rust-late-name-resolver-2.0.h index e40141c9238c..5703b152f7e7 100644 --- a/gcc/rust/resolve/rust-late-name-resolver-2.0.h +++ b/gcc/rust/resolve/rust-late-name-resolver-2.0.h @@ -48,6 +48,7 @@ public: void visit (AST::IdentifierExpr &) override; void visit (AST::StructExprFieldIdentifier &) override; void visit (AST::BreakExpr &) override; + void visit (AST::ContinueExpr &) override; void visit (AST::LoopLabel &) override; void visit (AST::PathInExpression &) override; void visit (AST::TypePath &) override; @@ -62,6 +63,8 @@ public: void visit (AST::ClosureExprInnerTyped &) override; private: + void resolve_label (AST::Lifetime &lifetime); + /* Setup Rust's builtin types (u8, i32, !...) in the resolver */ void setup_builtin_types (); diff --git a/gcc/testsuite/rust/compile/nr2/exclude b/gcc/testsuite/rust/compile/nr2/exclude index c688026a7b8f..665e0cf4d99b 100644 --- a/gcc/testsuite/rust/compile/nr2/exclude +++ b/gcc/testsuite/rust/compile/nr2/exclude @@ -12,7 +12,6 @@ privacy8.rs pub_restricted_1.rs pub_restricted_2.rs pub_restricted_3.rs -undeclared_label.rs use_1.rs issue-2905-2.rs derive_clone_enum3.rs
[gcc r15-9279] gccrs: Fix recusive type query and nullptr on type path
https://gcc.gnu.org/g:f388cac59df2704026b6a0585efba70154640b12 commit r15-9279-gf388cac59df2704026b6a0585efba70154640b12 Author: Philip Herron Date: Wed Apr 2 18:21:46 2025 +0100 gccrs: Fix recusive type query and nullptr on type path This was a small fix to sort out the segfault to check for nullptr on the TypePath cases for query type. But when this happened opened up a few bugs that were hidden under the carpet namely: compile/issue-2905-{1,2}.rs which has a recursive type query which needs to ne handled but now and error message is being output for the type path. This happens because we start resolving a generic struct: struct Wierd(A<(T,)>); So the child field A is also generic and the generic argument of the tuple of T needs to be applied to this generic field. This causes a chunk of code to do bounds checking to ensure the bounds are ok, this is also something that probably might change as generic types will have the bounds secified anyway but thats besides the case right now. So once this bounds checking occurs we endup looking at the impl block for Wierd which is also grand but we still havent finished resolving the parent type of Wierd which is recusive. But the query type system needs to check for that. The other issue was: compile/issue-3022.rs which is a resolution issue: impl, U> Foo for Bar The bound of Foo is added to T before U is resolved but this was hidden before the new error message was added. So now we have a generic arguements handler being used correctly all over the code base apart from 1 last case for Traits but we will deal with that later. This handles the case by setting up the type parameters upfront then sorting out their bounds. Fixes Rust-GCC#3625 gcc/rust/ChangeLog: * typecheck/rust-hir-trait-resolve.cc (TraitResolver::resolve_trait): new argument * typecheck/rust-hir-type-check-base.cc (TypeCheckBase::TypeCheckBase): new helper * typecheck/rust-hir-type-check-base.h: new helper prototype * typecheck/rust-hir-type-check-implitem.cc (TypeCheckTopLevelExternItem::visit): remove comment out code * typecheck/rust-hir-type-check-path.cc (TypeCheckExpr::resolve_root_path): check for null * typecheck/rust-hir-type-check-type.cc (TypeCheckType::resolve_root_path): likewise (TypeResolveGenericParam::Resolve): new args (TypeResolveGenericParam::ApplyAnyTraitBounds): new helper (TypeResolveGenericParam::apply_trait_bounds): new field (TypeResolveGenericParam::visit): update * typecheck/rust-hir-type-check-type.h: new args * typecheck/rust-hir-type-check.cc (TraitItemReference::get_type_from_fn): reuse helper * typecheck/rust-type-util.cc (query_type): check for recursive query * typecheck/rust-tyty-subst.cc (SubstitutionParamMapping::SubstitutionParamMapping): remove const (SubstitutionParamMapping::get_generic_param): likewise * typecheck/rust-tyty-subst.h: likewise * typecheck/rust-tyty-variance-analysis.cc (GenericTyVisitorCtx::process_type): likewise gcc/testsuite/ChangeLog: * rust/compile/issue-3625.rs: New test. Signed-off-by: Philip Herron Diff: --- gcc/rust/typecheck/rust-hir-trait-resolve.cc | 4 +- gcc/rust/typecheck/rust-hir-type-check-base.cc | 42 +- gcc/rust/typecheck/rust-hir-type-check-base.h | 8 +- gcc/rust/typecheck/rust-hir-type-check-implitem.cc | 163 + gcc/rust/typecheck/rust-hir-type-check-path.cc | 2 +- gcc/rust/typecheck/rust-hir-type-check-type.cc | 44 -- gcc/rust/typecheck/rust-hir-type-check-type.h | 11 +- gcc/rust/typecheck/rust-hir-type-check.cc | 33 + gcc/rust/typecheck/rust-type-util.cc | 37 + gcc/rust/typecheck/rust-tyty-subst.cc | 8 +- gcc/rust/typecheck/rust-tyty-subst.h | 6 +- gcc/rust/typecheck/rust-tyty-variance-analysis.cc | 2 +- gcc/testsuite/rust/compile/issue-3625.rs | 2 + 13 files changed, 144 insertions(+), 218 deletions(-) diff --git a/gcc/rust/typecheck/rust-hir-trait-resolve.cc b/gcc/rust/typecheck/rust-hir-trait-resolve.cc index a236fd78d7b1..e78c19263dc1 100644 --- a/gcc/rust/typecheck/rust-hir-trait-resolve.cc +++ b/gcc/rust/typecheck/rust-hir-trait-resolve.cc @@ -234,7 +234,9 @@ TraitResolver::resolve_trait (HIR::Trait *trait_reference) // The one exception is the implicit Self type of a trait bool apply_sized = !is_self; auto param_type - = TypeResolveGenericParam::Resolve (*generic_param, apply_sized); + = TypeResolveGenericParam::Resolve (*generic_param, true, +
[gcc r15-9292] gccrs: Visit loop label before predicate expression
https://gcc.gnu.org/g:d7bbb929a884bd429bc4b43d9fed57d57ab285b4 commit r15-9292-gd7bbb929a884bd429bc4b43d9fed57d57ab285b4 Author: Pierre-Emmanuel Patry Date: Tue Apr 1 12:02:31 2025 +0200 gccrs: Visit loop label before predicate expression If the label is referenced within the while predicate expression it has to be resolved before the latter. gcc/rust/ChangeLog: * ast/rust-ast-visitor.cc (DefaultASTVisitor::visit): Change default visit order. gcc/testsuite/ChangeLog: * rust/compile/nr2/exclude: Remove test from exclusion list. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/rust/ast/rust-ast-visitor.cc | 2 +- gcc/testsuite/rust/compile/nr2/exclude | 2 -- 2 files changed, 1 insertion(+), 3 deletions(-) diff --git a/gcc/rust/ast/rust-ast-visitor.cc b/gcc/rust/ast/rust-ast-visitor.cc index 6a81fa10aabd..73c6b1ee31e1 100644 --- a/gcc/rust/ast/rust-ast-visitor.cc +++ b/gcc/rust/ast/rust-ast-visitor.cc @@ -567,9 +567,9 @@ void DefaultASTVisitor::visit (AST::WhileLoopExpr &expr) { visit_outer_attrs (expr); - visit (expr.get_predicate_expr ()); if (expr.has_loop_label ()) visit (expr.get_loop_label ()); + visit (expr.get_predicate_expr ()); visit (expr.get_loop_block ()); } diff --git a/gcc/testsuite/rust/compile/nr2/exclude b/gcc/testsuite/rust/compile/nr2/exclude index 2f4585cbe8c4..c688026a7b8f 100644 --- a/gcc/testsuite/rust/compile/nr2/exclude +++ b/gcc/testsuite/rust/compile/nr2/exclude @@ -14,9 +14,7 @@ pub_restricted_2.rs pub_restricted_3.rs undeclared_label.rs use_1.rs -while_break_expr.rs issue-2905-2.rs -issue-266.rs derive_clone_enum3.rs derive-debug1.rs derive-default1.rs
[gcc/devel/rust/master] Rename label getter to unchecked
https://gcc.gnu.org/g:1d07cf75d5c558728d95a668a06dd7ecb4f5bb47 commit 1d07cf75d5c558728d95a668a06dd7ecb4f5bb47 Author: Pierre-Emmanuel Patry Date: Thu Apr 3 15:43:40 2025 +0200 Rename label getter to unchecked gcc/rust/ChangeLog: * ast/rust-ast-collector.cc (TokenCollector::visit): Update label getter call. * ast/rust-ast-visitor.cc (DefaultASTVisitor::visit): Likewise. * ast/rust-ast.cc (BreakExpr::as_string): Likewise. * hir/rust-ast-lower-expr.cc (ASTLoweringExpr::visit): Likewise. * resolve/rust-ast-resolve-expr.cc (ResolveExpr::visit): Likewise. * resolve/rust-late-name-resolver-2.0.cc (Late::visit): Likewise. * ast/rust-expr.h: Add optional getter and rename label getter to get_label_unchecked. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/rust/ast/rust-ast-collector.cc | 2 +- gcc/rust/ast/rust-ast-visitor.cc| 2 +- gcc/rust/ast/rust-ast.cc| 2 +- gcc/rust/ast/rust-expr.h| 7 +-- gcc/rust/hir/rust-ast-lower-expr.cc | 2 +- gcc/rust/resolve/rust-ast-resolve-expr.cc | 2 +- gcc/rust/resolve/rust-late-name-resolver-2.0.cc | 2 +- 7 files changed, 11 insertions(+), 8 deletions(-) diff --git a/gcc/rust/ast/rust-ast-collector.cc b/gcc/rust/ast/rust-ast-collector.cc index d81e51e89b66..9a7164c3dac9 100644 --- a/gcc/rust/ast/rust-ast-collector.cc +++ b/gcc/rust/ast/rust-ast-collector.cc @@ -1287,7 +1287,7 @@ TokenCollector::visit (BreakExpr &expr) { push (Rust::Token::make (BREAK, expr.get_locus ())); if (expr.has_label ()) -visit (expr.get_label ()); +visit (expr.get_label_unchecked ()); if (expr.has_break_expr ()) visit (expr.get_break_expr ()); } diff --git a/gcc/rust/ast/rust-ast-visitor.cc b/gcc/rust/ast/rust-ast-visitor.cc index 21230113b7b5..1a3fd65ce800 100644 --- a/gcc/rust/ast/rust-ast-visitor.cc +++ b/gcc/rust/ast/rust-ast-visitor.cc @@ -486,7 +486,7 @@ DefaultASTVisitor::visit (AST::BreakExpr &expr) { visit_outer_attrs (expr); if (expr.has_label ()) -visit (expr.get_label ()); +visit (expr.get_label_unchecked ()); if (expr.has_break_expr ()) visit (expr.get_break_expr ()); diff --git a/gcc/rust/ast/rust-ast.cc b/gcc/rust/ast/rust-ast.cc index 2311c579fd6c..81e5c93422b7 100644 --- a/gcc/rust/ast/rust-ast.cc +++ b/gcc/rust/ast/rust-ast.cc @@ -2183,7 +2183,7 @@ BreakExpr::as_string () const std::string str ("break "); if (has_label ()) -str += get_label ().as_string () + " "; +str += get_label_unchecked ().as_string () + " "; if (has_break_expr ()) str += break_expr->as_string (); diff --git a/gcc/rust/ast/rust-expr.h b/gcc/rust/ast/rust-expr.h index 4c832f9a06f4..84cdfdb46780 100644 --- a/gcc/rust/ast/rust-expr.h +++ b/gcc/rust/ast/rust-expr.h @@ -2982,8 +2982,11 @@ public: outer_attrs = std::move (new_attrs); } - LoopLabel &get_label () { return label.value (); } - const LoopLabel &get_label () const { return label.value (); } + LoopLabel &get_label_unchecked () { return label.value (); } + const LoopLabel &get_label_unchecked () const { return label.value (); } + + tl::optional &get_label () { return label; } + const tl::optional &get_label () const { return label; } Expr::Kind get_expr_kind () const override { return Expr::Kind::Break; } diff --git a/gcc/rust/hir/rust-ast-lower-expr.cc b/gcc/rust/hir/rust-ast-lower-expr.cc index 2ee5591f1526..3f040d472618 100644 --- a/gcc/rust/hir/rust-ast-lower-expr.cc +++ b/gcc/rust/hir/rust-ast-lower-expr.cc @@ -599,7 +599,7 @@ ASTLoweringExpr::visit (AST::BreakExpr &expr) { tl::optional break_label = tl::nullopt; if (expr.has_label ()) -break_label = lower_lifetime (expr.get_label ().get_lifetime ()); +break_label = lower_lifetime (expr.get_label_unchecked ().get_lifetime ()); HIR::Expr *break_expr = expr.has_break_expr () diff --git a/gcc/rust/resolve/rust-ast-resolve-expr.cc b/gcc/rust/resolve/rust-ast-resolve-expr.cc index c0ce827606be..2aebaaf999df 100644 --- a/gcc/rust/resolve/rust-ast-resolve-expr.cc +++ b/gcc/rust/resolve/rust-ast-resolve-expr.cc @@ -471,7 +471,7 @@ ResolveExpr::visit (AST::BreakExpr &expr) { if (expr.has_label ()) { - auto label = expr.get_label ().get_lifetime (); + auto label = expr.get_label_unchecked ().get_lifetime (); if (label.get_lifetime_type () != AST::Lifetime::LifetimeType::NAMED) { rust_error_at (label.get_locus (), diff --git a/gcc/rust/resolve/rust-late-name-resolver-2.0.cc b/gcc/rust/resolve/rust-late-name-resolver-2.0.cc index 7244d200ab1f..c140fa07f9b8 100644 --- a/gcc/rust/resolve/rust-late-name-resolver-2.0.cc +++ b/gcc/rust/resolve/rust-late-name-resolver-2.0.cc @@ -188,7 +188,7 @@ void Late::visit (AST::BreakExpr &expr) { if (expr.has_label ()) -resolve_label (expr.get_label ().get_lifetime
[gcc r15-9278] gccrs: Fix ICE when there are 2 functions named main
https://gcc.gnu.org/g:b1afef95601fd2f0323dd508a171267ff04f755b commit r15-9278-gb1afef95601fd2f0323dd508a171267ff04f755b Author: Philip Herron Date: Wed Apr 2 16:16:47 2025 +0100 gccrs: Fix ICE when there are 2 functions named main We need to setup the main_identifier_node for MAIN_DECL_P checks in the middle-end. But it is valid to have a main function/method on impl blocks. So we need to flag if this is a "root" item or not, which is one that is jsut an HIR::Function on part of the Crate::items as oppposed to a HIR::Function which is part of an HIR::ImplBlock as part of the HIR::Crate. Some small cleanups have been added here too. Fixes Rust-GCC#3648 gcc/rust/ChangeLog: * backend/rust-compile-base.cc: new flag is_root_item * backend/rust-compile-base.h: update prototype * backend/rust-compile-implitem.cc (CompileTraitItem::visit): update call * backend/rust-compile-implitem.h: remove old debug internal error * backend/rust-compile-item.cc (CompileItem::visit): update call * backend/rust-compile-item.h: remove old debug * backend/rust-compile-resolve-path.cc (HIRCompileBase::query_compile): update calls * backend/rust-compile.cc: likewise * typecheck/rust-hir-trait-resolve.cc (TraitResolver::resolve_path_to_trait): remove assertion and error gcc/testsuite/ChangeLog: * rust/compile/issue-3648.rs: New test. Signed-off-by: Philip Herron Diff: --- gcc/rust/backend/rust-compile-base.cc | 4 ++-- gcc/rust/backend/rust-compile-base.h | 3 ++- gcc/rust/backend/rust-compile-implitem.cc | 2 +- gcc/rust/backend/rust-compile-implitem.h | 6 -- gcc/rust/backend/rust-compile-item.cc | 6 +- gcc/rust/backend/rust-compile-item.h | 4 gcc/rust/backend/rust-compile-resolve-path.cc | 9 - gcc/rust/backend/rust-compile.cc | 2 +- gcc/rust/typecheck/rust-hir-trait-resolve.cc | 8 +++- gcc/testsuite/rust/compile/issue-3648.rs | 8 10 files changed, 30 insertions(+), 22 deletions(-) diff --git a/gcc/rust/backend/rust-compile-base.cc b/gcc/rust/backend/rust-compile-base.cc index fdbca7f1558a..b6bee8f9c2f1 100644 --- a/gcc/rust/backend/rust-compile-base.cc +++ b/gcc/rust/backend/rust-compile-base.cc @@ -663,7 +663,7 @@ get_abi (const AST::AttrVec &outer_attrs, tree HIRCompileBase::compile_function ( - const std::string &fn_name, HIR::SelfParam &self_param, + bool is_root_item, const std::string &fn_name, HIR::SelfParam &self_param, std::vector &function_params, const HIR::FunctionQualifiers &qualifiers, HIR::Visibility &visibility, AST::AttrVec &outer_attrs, location_t locus, HIR::BlockExpr *function_body, @@ -674,7 +674,7 @@ HIRCompileBase::compile_function ( = canonical_path.get () + fntype->subst_as_string (); // we don't mangle the main fn since we haven't implemented the main shim - bool is_main_fn = fn_name.compare ("main") == 0; + bool is_main_fn = fn_name.compare ("main") == 0 && is_root_item; if (is_main_fn) { rust_assert (!main_identifier_node); diff --git a/gcc/rust/backend/rust-compile-base.h b/gcc/rust/backend/rust-compile-base.h index 4b4f8b09256e..64c8106d1c28 100644 --- a/gcc/rust/backend/rust-compile-base.h +++ b/gcc/rust/backend/rust-compile-base.h @@ -102,7 +102,8 @@ protected: HIR::Expr &const_value_expr, location_t locus, location_t expr_locus); - tree compile_function (const std::string &fn_name, HIR::SelfParam &self_param, + tree compile_function (bool is_root_item, const std::string &fn_name, +HIR::SelfParam &self_param, std::vector &function_params, const HIR::FunctionQualifiers &qualifiers, HIR::Visibility &visibility, AST::AttrVec &outer_attrs, diff --git a/gcc/rust/backend/rust-compile-implitem.cc b/gcc/rust/backend/rust-compile-implitem.cc index 71b3e8d3002d..1230c85c57ca 100644 --- a/gcc/rust/backend/rust-compile-implitem.cc +++ b/gcc/rust/backend/rust-compile-implitem.cc @@ -117,7 +117,7 @@ CompileTraitItem::visit (HIR::TraitItemFunc &func) auto vis = HIR::Visibility (HIR::Visibility::VisType::PUBLIC); HIR::TraitFunctionDecl &function = func.get_decl (); tree fndecl -= compile_function (function.get_function_name ().as_string (), += compile_function (false, function.get_function_name ().as_string (), function.get_self (), function.get_function_params (), function.get_qualifiers (), vis, func.get_outer_attrs (), func.get_locus (), diff --git a/gcc/rust/backend/rust-compile-implitem.h b/gcc/rust/backend/rust-compile-implitem.h index d2ef98920906..2d18dbfffcba 100644 --- a/gcc/rust/backend/rust-
[gcc r15-9306] lto: Add & ~CF_SET into lto-opts.cc [PR119625]
https://gcc.gnu.org/g:15baa0055601a00b77e2e0ed6259bbc9e5ea5fa9 commit r15-9306-g15baa0055601a00b77e2e0ed6259bbc9e5ea5fa9 Author: Jakub Jelinek Date: Tue Apr 8 11:53:34 2025 +0200 lto: Add & ~CF_SET into lto-opts.cc [PR119625] The following patch uses & ~CF_SET so that we get the -fcf-protection= options into .gnu.lto_.opts section even when it has CF_SET bit set. 2025-04-08 Jakub Jelinek PR lto/119625 * lto-opts.cc (lto_write_options): Mask of CF_SET from global_options.x_flag_cf_protection. Diff: --- gcc/lto-opts.cc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gcc/lto-opts.cc b/gcc/lto-opts.cc index 3959598b497c..62a3fb280636 100644 --- a/gcc/lto-opts.cc +++ b/gcc/lto-opts.cc @@ -97,7 +97,7 @@ lto_write_options (void) if (!OPTION_SET_P (flag_cf_protection)) { const char *cf_protection = NULL; - switch (global_options.x_flag_cf_protection) + switch (global_options.x_flag_cf_protection & ~CF_SET) { case CF_NONE: cf_protection = "-fcf-protection=none"; break; case CF_FULL: cf_protection = "-fcf-protection=full"; break;
[gcc r15-9273] libstdc++: Fix use-after-free in std::format [PR119671]
https://gcc.gnu.org/g:e33b62eed7fd0a82d758b23252d288585b6790d2 commit r15-9273-ge33b62eed7fd0a82d758b23252d288585b6790d2 Author: Jonathan Wakely Date: Mon Apr 7 19:52:55 2025 +0100 libstdc++: Fix use-after-free in std::format [PR119671] When formatting floating-point values to wide strings there's a case where we invalidate a std::wstring buffer while a std::wstring_view is still referring to it. libstdc++-v3/ChangeLog: PR libstdc++/119671 * include/std/format (__formatter_fp::format): Do not invalidate __wstr unless _M_localized returns a valid string. * testsuite/std/format/functions/format.cc: Check wide string formatting of floating-point types with classic locale. Reviewed-by: Tomasz Kaminski Diff: --- libstdc++-v3/include/std/format | 6 +++--- libstdc++-v3/testsuite/std/format/functions/format.cc | 12 2 files changed, 15 insertions(+), 3 deletions(-) diff --git a/libstdc++-v3/include/std/format b/libstdc++-v3/include/std/format index 01a53143d1c5..2e9319cdda63 100644 --- a/libstdc++-v3/include/std/format +++ b/libstdc++-v3/include/std/format @@ -1838,9 +1838,9 @@ namespace __format if (_M_spec._M_localized && __builtin_isfinite(__v)) { - __wstr = _M_localize(__str, __expc, __fc.locale()); - if (!__wstr.empty()) - __str = __wstr; + auto __s = _M_localize(__str, __expc, __fc.locale()); + if (!__s.empty()) + __str = __wstr = std::move(__s); } size_t __width = _M_spec._M_get_width(__fc); diff --git a/libstdc++-v3/testsuite/std/format/functions/format.cc b/libstdc++-v3/testsuite/std/format/functions/format.cc index 000f2671816d..93c33b456e64 100644 --- a/libstdc++-v3/testsuite/std/format/functions/format.cc +++ b/libstdc++-v3/testsuite/std/format/functions/format.cc @@ -370,6 +370,18 @@ test_wchar() // P2909R4 Fix formatting of code units as integers (Dude, where’s my char?) s = std::format(L"{:d} {:d}", wchar_t(-1), char(-1)); VERIFY( s.find('-') == std::wstring::npos ); + + auto ws = std::format(L"{:L}", 0.5); + VERIFY( ws == L"0.5" ); + // The default C locale. + std::locale cloc = std::locale::classic(); + // PR libstdc++/119671 use-after-free formatting floating-point to wstring + ws = std::format(cloc, L"{:L}", 0.5); + VERIFY( ws == L"0.5" ); + // A locale with no name, but with the same facets as the C locale. + std::locale locx(cloc, &std::use_facet>(cloc)); + ws = std::format(locx, L"{:L}", 0.5); + VERIFY( ws == L"0.5" ); } void
[gcc r15-9312] riscv: Fix a typo in config/riscv/freebsd.h [PR119678]
https://gcc.gnu.org/g:f53c5cde64770d6c175737a50fea81feba80 commit r15-9312-gf53c5cde64770d6c175737a50fea81feba80 Author: Jakub Jelinek Date: Tue Apr 8 12:39:16 2025 +0200 riscv: Fix a typo in config/riscv/freebsd.h [PR119678] The r15-1124 commit had a typo in one of the FBSD_LINK_PG_NOTE macro uses. Fixed thusly, tested with ../configure --target riscv64-unknown-freebsd14 --disable-bootstrap --enable-languages=c --disable-libsanitizer --disable-libgomp make -j32 Before it failed while compiling gcc.cc: In file included from ./tm.h:44, from ../../gcc/gcc.cc:35: ../../gcc/config/riscv/freebsd.h:45:5: error: expected ‘,’ or ‘;’ before ‘FBSD_LINK_PG_NOTES’ 45 | " FBSD_LINK_PG_NOTES " \ | ^~ ../../gcc/gcc.cc:1211:32: note: in expansion of macro ‘LINK_SPEC’ Now it fails later on during libgcc configury because I don't have corresponding binutils. 2025-04-08 Jakub Jelinek PR target/119678 * config/riscv/freebsd.h (LINK_SPEC): Use FBSD_LINK_PG_NOTE rather than non-existing FBSD_LINK_PG_NOTES. Diff: --- gcc/config/riscv/freebsd.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gcc/config/riscv/freebsd.h b/gcc/config/riscv/freebsd.h index 2dc705532d83..217e0ac15e6f 100644 --- a/gcc/config/riscv/freebsd.h +++ b/gcc/config/riscv/freebsd.h @@ -42,7 +42,7 @@ along with GCC; see the file COPYING3. If not see #define LINK_SPEC "\ -melf" XLEN_SPEC DEFAULT_ENDIAN_SPEC "riscv \ %{p:%nconsider using `-pg' instead of `-p' with gprof (1)} \ - " FBSD_LINK_PG_NOTES " \ + " FBSD_LINK_PG_NOTE "\ %{v:-V} \ %{assert*} %{R*} %{rpath*} %{defsym*}\ -X \
[gcc/devel/rust/master] nr2.0: Improve test script
https://gcc.gnu.org/g:b9aaa6192f3310a0cb26f7773b31703a8c9c544c commit b9aaa6192f3310a0cb26f7773b31703a8c9c544c Author: Owen Avery Date: Sun Mar 30 19:08:45 2025 -0400 nr2.0: Improve test script gcc/testsuite/ChangeLog: * rust/compile/nr2/compile.exp: Avoid absolute paths in output, adjust phrasing of output, and avoid false XPASS output when tests are run in parallel. Signed-off-by: Owen Avery Diff: --- gcc/testsuite/rust/compile/nr2/compile.exp | 32 +- 1 file changed, 18 insertions(+), 14 deletions(-) diff --git a/gcc/testsuite/rust/compile/nr2/compile.exp b/gcc/testsuite/rust/compile/nr2/compile.exp index 35637f11ee8c..4d91dd004a3d 100644 --- a/gcc/testsuite/rust/compile/nr2/compile.exp +++ b/gcc/testsuite/rust/compile/nr2/compile.exp @@ -47,18 +47,22 @@ namespace eval rust-nr2-ns { set tests_expect_ok "" set tests_expect_err "" +set compile_dir [list {*}[file split $srcdir] {*}[file split $subdir]] +set compile_dir [lreplace $compile_dir end end] + foreach test_dir $test_dirs { -set directory [list {*}[file split $srcdir] {*}[file split $subdir]] - set directory [lreplace $directory end end] - set directory [list {*}$directory {*}$test_dir] -foreach test [lsort [glob -nocomplain -tails -directory [file join {*}$directory] *.rs]] { +foreach test [lsort [glob -nocomplain -tails -directory [file join {*}$compile_dir {*}$test_dir] *.rs]] { # use '/' as the path seperator for entries in the exclude file set test_lbl [join [list {*}$test_dir $test] "/"] set idx [lsearch -exact -sorted $exclude $test_lbl] if {$idx == -1} { - lappend tests_expect_ok [file join {*}$directory $test] + if {[runtest_file_p $runtests [file join {*}$compile_dir {*}$test_dir $test]]} { + lappend tests_expect_ok [list {*}$test_dir $test] + } } else { - lappend tests_expect_err [file join {*}$directory $test] + if {[runtest_file_p $runtests [file join {*}$compile_dir {*}$test_dir $test]]} { + lappend tests_expect_err [list {*}$test_dir $test] + } set exclude [lreplace $exclude $idx $idx] } } @@ -83,10 +87,10 @@ namespace eval rust-nr2-ns { variable record_test_out switch $type { FAIL { - lappend record_test_out "$type: $msg" + lappend record_test_out [list $type $msg] } XPASS { - lappend record_test_out "$type: $msg" + lappend record_test_out [list $type $msg] } } } @@ -109,23 +113,23 @@ namespace eval rust-nr2-ns { # check for unexpected failures foreach test $tests_expect_ok { -set fails [try_test $test] +set fails [try_test [file join {*}$compile_dir {*}$test]] if {[llength $fails] != 0} { foreach ent $fails { - record_test FAIL "$test: nr2 failure: $ent" + record_test [lindex $ent 0] "on nr2: [lindex $ent 1]" } } else { - record_test PASS "$test: nr2 success" + record_test PASS "[file join {*}$test] on nr2" } } #check for unexpected successes foreach test $tests_expect_err { -set fails [try_test $test] +set fails [try_test [file join {*}$compile_dir {*}$test]] if {[llength $fails] == 0} { - record_test XPASS "$test: nr2 unexpectedly passed" + record_test XPASS "[file join {*}$test] on nr2" } else { - record_test XFAIL "$test: nr2 was rightfully excluded" + record_test XFAIL "[file join {*}$test] on nr2 was rightfully excluded" } } }
[gcc r15-9316] simplify-rtx: Fix up POPCOUNT optimization [PR119672]
https://gcc.gnu.org/g:04918a2d3f20b02ac3efad1096c33894d57789a0 commit r15-9316-g04918a2d3f20b02ac3efad1096c33894d57789a0 Author: Jakub Jelinek Date: Tue Apr 8 15:14:58 2025 +0200 simplify-rtx: Fix up POPCOUNT optimization [PR119672] The gcc.dg/vect/pr113281-1.c test and many others ICE on riscv since presumably the r15-9238 change which allowed more cases of vector modes in simplify_const_relational_operation. In the testcase it is EQ of (popcount:SI (unspec:RVVMF32BI [ (and:RVVMF32BI (const_vector:RVVMF32BI repeat [ (const_int 1 [0x1]) ]) (reg:RVVMF32BI 147 [ mask__6.8_35 ])) (reg:SI 143 [ _41 ]) (const_int 0 [0]) (reg:SI 66 vl) (reg:SI 67 vtype) ] UNSPEC_VPREDICATE)) and (const_int 0 [0]) which it tries to fold as EQ comparison of (unspec:RVVMF32BI [ (and:RVVMF32BI (const_vector:RVVMF32BI repeat [ (const_int 1 [0x1]) ]) (reg:RVVMF32BI 147 [ mask__6.8_35 ])) (reg:SI 143 [ _41 ]) (const_int 0 [0]) (reg:SI 66 vl) (reg:SI 67 vtype) ] UNSPEC_VPREDICATE) with (const_int 0 [0]) which ICEs because const0_rtx isn't a vector. Fixed by using CONST0_RTX, so that we pass (const_vector:RVVMF32BI repeat [ (const_int 0 [0]) ]) instead. 2025-04-08 Jakub Jelinek PR rtl-optimization/119672 * simplify-rtx.cc (simplify_context::simplify_relational_operation_1): For POPCOUNT == 0 or != 0 optimizations use CONST0_RTX (GET_MODE (XEXP (op0, 0))) rather than const0_rtx. Diff: --- gcc/simplify-rtx.cc | 6 -- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/gcc/simplify-rtx.cc b/gcc/simplify-rtx.cc index 6f969effdf99..88d31a71c05a 100644 --- a/gcc/simplify-rtx.cc +++ b/gcc/simplify-rtx.cc @@ -6465,14 +6465,16 @@ simplify_context::simplify_relational_operation_1 (rtx_code code, case LEU: /* (eq (popcount x) (const_int 0)) -> (eq x (const_int 0)). */ return simplify_gen_relational (EQ, mode, GET_MODE (XEXP (op0, 0)), - XEXP (op0, 0), const0_rtx); + XEXP (op0, 0), + CONST0_RTX (GET_MODE (XEXP (op0, 0; case NE: case GT: case GTU: /* (ne (popcount x) (const_int 0)) -> (ne x (const_int 0)). */ return simplify_gen_relational (NE, mode, GET_MODE (XEXP (op0, 0)), - XEXP (op0, 0), const0_rtx); + XEXP (op0, 0), + CONST0_RTX (GET_MODE (XEXP (op0, 0; default: break;
[gcc r15-9317] cobol: Further fixes for cobol cross-compilation from 32-bit arches [PR119364]
https://gcc.gnu.org/g:1b5b02be5740b69f670b1591ac63eb6a69ff1f79 commit r15-9317-g1b5b02be5740b69f670b1591ac63eb6a69ff1f79 Author: Jakub Jelinek Date: Tue Apr 8 15:57:45 2025 +0200 cobol: Further fixes for cobol cross-compilation from 32-bit arches [PR119364] On top of https://gcc.gnu.org/pipermail/gcc-patches/2025-April/680256.html patch this brings make check-cobol when using the cross compiler from 32-bit host to x86_64-linux to the following: Running /home/jakub/src/gcc/gcc/testsuite/cobol.dg/dg.exp ... FAIL: cobol.dg/group1/declarative_1.cob -O0 execution test FAIL: cobol.dg/group1/declarative_1.cob -O1 execution test FAIL: cobol.dg/group1/declarative_1.cob -O2 execution test FAIL: cobol.dg/group1/declarative_1.cob -O3 -fomit-frame-pointer -funroll-loops -fpeel-loops -ftracer -finline-functions execution test FAIL: cobol.dg/group1/declarative_1.cob -O3 -g execution test FAIL: cobol.dg/group1/declarative_1.cob -Os execution test === cobol Summary === # of expected passes3123 # of unexpected failures6 # of expected failures 6 (which has some analysis but not a fix yet). This patch fixes various cases where host size of various types (void *, int, size_t, unsigned char) is used in place where size of those types in bytes on the target should be used instead. At least the size of void * and size_t actually differns between ilp32 hosts and lp64 targets, int could be different in theory as well but we actually don't support 16-bit ints on the host side and only support lp64 targets right now for cobol, and finally sizeof(unsigned char) is always 1, so there is no point to multiply by that and it is still wrong to use host sizeof for the target decisions. 2025-04-08 Jakub Jelinek PR cobol/119364 * genapi.cc (function_handle_from_name): Use sizeof_pointer. (parser_file_add): Use int_size_in_bytes(VOID_P) and int_size_in_bytes(int). (inspect_tally): Use int_size_in_bytes(VOID_P). (inspect_replacing): Likewise. (gg_array_of_field_pointers): Likewise. (gg_array_of_file_pointers): Likewise. (parser_set_pointers): Use sizeof_pointer. * cobol1.cc (create_our_type_nodes_init): Use int_size_in_bytes(SIZE_T) and int_size_in_bytes(VOID_P). * gengen.cc (gg_array_of_size_t): Use int_size_in_bytes(SIZE_T). (gg_array_of_bytes): Just use N, don't multiply it by sizeof(unsigned char). * parse.y: Include tree.h. Use int_size_in_bytes(ptr_type_node). Diff: --- gcc/cobol/cobol1.cc | 4 ++-- gcc/cobol/genapi.cc | 31 +++ gcc/cobol/gengen.cc | 5 +++-- gcc/cobol/parse.y | 6 -- 4 files changed, 28 insertions(+), 18 deletions(-) diff --git a/gcc/cobol/cobol1.cc b/gcc/cobol/cobol1.cc index 0d07c460d416..1e690ff4ba54 100644 --- a/gcc/cobol/cobol1.cc +++ b/gcc/cobol/cobol1.cc @@ -166,8 +166,8 @@ create_our_type_nodes_init() long_double_ten_node = build_real_from_int_cst( LONGDOUBLE, build_int_cst_type(INT,10)); - sizeof_size_t = build_int_cst_type(SIZE_T, sizeof(size_t)); - sizeof_pointer = build_int_cst_type(SIZE_T, sizeof(void *)); + sizeof_size_t = build_int_cst_type(SIZE_T, int_size_in_bytes(SIZE_T)); + sizeof_pointer = build_int_cst_type(SIZE_T, int_size_in_bytes(VOID_P)); bool_true_node = build2(EQ_EXPR, integer_type_node, diff --git a/gcc/cobol/genapi.cc b/gcc/cobol/genapi.cc index fbe0bbc75dc8..c91237bd8d2c 100644 --- a/gcc/cobol/genapi.cc +++ b/gcc/cobol/genapi.cc @@ -787,13 +787,13 @@ function_handle_from_name(cbl_refer_t &name, { gg_memcpy(gg_get_address_of(function_handle), member(name.field->var_decl_node, "data"), -build_int_cst_type(SIZE_T, sizeof(void *))); +sizeof_pointer); } else { gg_memcpy(gg_get_address_of(function_handle), qualified_data_source(name), -build_int_cst_type(SIZE_T, sizeof(void *))); +sizeof_pointer); } return function_handle; } @@ -8917,8 +8917,8 @@ parser_file_add(struct cbl_file_t *file) gg_assign(array_of_keys, gg_cast(build_pointer_type(cblc_field_p_type_node), gg_malloc(build_int_cst_type(SIZE_T, -(number_of_key_fields+1) -*sizeof(void *); + (number_of_key_fields+1) + *int_size_in_bytes(VOID_P); strcpy(achName, "_"); strcat(achName, file->name); @@
[gcc r15-9305] gccrs: nr2.0: Adjust test macro6.rs
https://gcc.gnu.org/g:29ed33631f0eb4c88c8b253d5245958304102217 commit r15-9305-g29ed33631f0eb4c88c8b253d5245958304102217 Author: Owen Avery Date: Sun Mar 23 21:40:47 2025 -0400 gccrs: nr2.0: Adjust test macro6.rs gcc/testsuite/ChangeLog: * rust/compile/macros/mbe/macro6.rs: Remove call of undefined function. * rust/compile/nr2/exclude: Remove macros/mbe/macro6.rs. Signed-off-by: Owen Avery Diff: --- gcc/testsuite/rust/compile/macros/mbe/macro6.rs | 2 +- gcc/testsuite/rust/compile/nr2/exclude | 1 - 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/gcc/testsuite/rust/compile/macros/mbe/macro6.rs b/gcc/testsuite/rust/compile/macros/mbe/macro6.rs index 9c54a674533d..bbaaa25eb52c 100644 --- a/gcc/testsuite/rust/compile/macros/mbe/macro6.rs +++ b/gcc/testsuite/rust/compile/macros/mbe/macro6.rs @@ -1,6 +1,6 @@ macro_rules! zero_or_one { ($($a:literal)?) => { -f(); +1 + 2; } } diff --git a/gcc/testsuite/rust/compile/nr2/exclude b/gcc/testsuite/rust/compile/nr2/exclude index 9502f3981912..4772517c47e4 100644 --- a/gcc/testsuite/rust/compile/nr2/exclude +++ b/gcc/testsuite/rust/compile/nr2/exclude @@ -3,7 +3,6 @@ cfg1.rs generics9.rs issue-3315-2.rs lookup_err1.rs -macros/mbe/macro6.rs multiple_bindings1.rs multiple_bindings2.rs privacy5.rs
[gcc r15-9315] c: fix checking for a tag for variably modified tagged types [PR119612]
https://gcc.gnu.org/g:a3382d9d675f42db96a51d902afc49a0a4cfadee commit r15-9315-ga3382d9d675f42db96a51d902afc49a0a4cfadee Author: Martin Uecker Date: Fri Apr 4 21:01:48 2025 +0200 c: fix checking for a tag for variably modified tagged types [PR119612] The checking assertion added for PR118765 did not take into account that add_decl_expr can change TYPE_NAME to a TYPE_DECL with no name for certain cases of variably modified types. This also implies that we might sometimes not reliably detect the absence of a tag when only considering TYPE_NAME. This patch introduces a new helper function c_type_tag to reliable compute the tag for a tagged types and uses it for code where the switch to C23 may cause regressions. PR c/119612 gcc/c/ChangeLog: * c-tree.h (c_type_tag): Add prototype. * c-typeck.cc (c_type_tag): New function. (tagged_types_tu_compatible_p, composite_type_internal): Use c_type_tag. * c-decl.cc (c_struct_hasher::hash, previous_tag): Use c_type_tag. gcc/testsuite/ChangeLog: * gcc.dg/gnu23-tag-6.c: New test. * gcc.dg/pr119612.c: New test. Diff: --- gcc/c/c-decl.cc| 5 +++-- gcc/c/c-tree.h | 1 + gcc/c/c-typeck.cc | 38 -- gcc/testsuite/gcc.dg/gnu23-tag-6.c | 27 +++ gcc/testsuite/gcc.dg/pr119612.c| 9 + 5 files changed, 64 insertions(+), 16 deletions(-) diff --git a/gcc/c/c-decl.cc b/gcc/c/c-decl.cc index c778c7febfa0..8c420f229762 100644 --- a/gcc/c/c-decl.cc +++ b/gcc/c/c-decl.cc @@ -659,7 +659,8 @@ c_struct_hasher::hash (tree type) inchash::hash hstate; hstate.add_int (TREE_CODE (type)); - hstate.add_object (TYPE_NAME (type)); + tree tag = c_type_tag (type); + hstate.add_object (tag); return hstate.end (); } @@ -2073,7 +2074,7 @@ static tree previous_tag (tree type) { struct c_binding *b = NULL; - tree name = TYPE_NAME (type); + tree name = c_type_tag (type); if (name) b = I_TAG_BINDING (name); diff --git a/gcc/c/c-tree.h b/gcc/c/c-tree.h index 743ec5cbae61..2098120de297 100644 --- a/gcc/c/c-tree.h +++ b/gcc/c/c-tree.h @@ -795,6 +795,7 @@ c_type_unspecified_p (tree t) } extern bool char_type_p (tree); +extern tree c_type_tag (const_tree t); extern tree c_objc_common_truthvalue_conversion (location_t, tree, tree = integer_type_node); extern tree require_complete_type (location_t, tree); diff --git a/gcc/c/c-typeck.cc b/gcc/c/c-typeck.cc index 19e79b554dca..3870e8a15587 100644 --- a/gcc/c/c-typeck.cc +++ b/gcc/c/c-typeck.cc @@ -577,7 +577,7 @@ c_build_functype_attribute_variant (tree ntype, tree otype, tree attrs) } /* Given a type which could be a typedef name, make sure to return the - original type. */ + original type. See set_underlying_type. */ static const_tree c_type_original (const_tree t) { @@ -591,6 +591,26 @@ c_type_original (const_tree t) return t; } +/* Return the tag for a tagged type. */ +tree +c_type_tag (const_tree t) +{ + gcc_assert (RECORD_OR_UNION_TYPE_P (t) || TREE_CODE (t) == ENUMERAL_TYPE); + const_tree orig = c_type_original (t); + tree name = TYPE_NAME (orig); + if (!name) +return NULL_TREE; + if (TREE_CODE (name) == TYPE_DECL) +{ + /* A TYPE_DECL added by add_decl_expr. */ + gcc_checking_assert (!DECL_NAME (name)); + return NULL_TREE; +} + gcc_checking_assert (TREE_CODE (name) == IDENTIFIER_NODE); + return name; +} + + /* Return the composite type of two compatible types. @@ -744,7 +764,7 @@ composite_type_internal (tree t1, tree t2, struct composite_cache* cache) if (flag_isoc23 && !comptypes_same_p (t1, t2)) { /* Go to the original type to get the right tag. */ - tree tag = TYPE_NAME (c_type_original (const_cast (t1))); + tree tag = c_type_tag (t1); gcc_checking_assert (COMPLETE_TYPE_P (t1) && COMPLETE_TYPE_P (t2)); gcc_checking_assert (!tag || comptypes (t1, t2)); @@ -1807,17 +1827,7 @@ tagged_types_tu_compatible_p (const_tree t1, const_tree t2, { tree s1, s2; - /* We have to verify that the tags of the types are the same. This - is harder than it looks because this may be a typedef, so we have - to go look at the original type. */ - t1 = c_type_original (t1); - t2 = c_type_original (t2); - gcc_checking_assert (!TYPE_NAME (t1) - || TREE_CODE (TYPE_NAME (t1)) == IDENTIFIER_NODE); - gcc_checking_assert (!TYPE_NAME (t2) - || TREE_CODE (TYPE_NAME (t2)) == IDENTIFIER_NODE); - - if (TYPE_NAME (t1) != TYPE_NAME (t2)) + if (c_type_tag (t1) != c_type_tag (t2)) return false; /* When forming equivalence classes for TYPE_CANONICAL in C23, we treat @@ -1828,7 +1838,7 @@ tagged_types_tu_compatible_p (const_
[gcc r15-9284] gccrs: hir: Add default qualifier to function, lower it properly
https://gcc.gnu.org/g:6410c1dddabc0fbb226f14e95590b1276574e8fd commit r15-9284-g6410c1dddabc0fbb226f14e95590b1276574e8fd Author: Arthur Cohen Date: Tue Apr 1 17:45:28 2025 +0200 gccrs: hir: Add default qualifier to function, lower it properly gcc/rust/ChangeLog: * ast/rust-ast.cc (Function::Function): Rename is_default -> has_default. (Function::operator=): Likewise. * ast/rust-item.h (class Function): Add `is_default` method. * hir/rust-ast-lower-implitem.cc (ASTLowerImplItem::visit): Lower default qualifier. * hir/rust-ast-lower-item.cc (ASTLoweringItem::visit): Likewise. * hir/tree/rust-hir-item.cc (Function::Function): Add `is_default` member. (Function::operator=): Likewise. * hir/tree/rust-hir-item.h (enum class Defaultness): New enum. (class Function): Use it. gcc/testsuite/ChangeLog: * rust/compile/min_specialization1.rs: New test. Diff: --- gcc/rust/ast/rust-ast.cc | 4 ++-- gcc/rust/ast/rust-item.h | 8 +--- gcc/rust/hir/rust-ast-lower-implitem.cc | 6 +- gcc/rust/hir/rust-ast-lower-item.cc | 5 - gcc/rust/hir/tree/rust-hir-item.cc| 9 ++--- gcc/rust/hir/tree/rust-hir-item.h | 17 - gcc/testsuite/rust/compile/min_specialization1.rs | 15 +++ 7 files changed, 53 insertions(+), 11 deletions(-) diff --git a/gcc/rust/ast/rust-ast.cc b/gcc/rust/ast/rust-ast.cc index ab82303879c9..e4a1b369970e 100644 --- a/gcc/rust/ast/rust-ast.cc +++ b/gcc/rust/ast/rust-ast.cc @@ -1068,7 +1068,7 @@ Function::Function (Function const &other) : VisItem (other), ExternalItem (other.get_node_id ()), qualifiers (other.qualifiers), function_name (other.function_name), where_clause (other.where_clause), locus (other.locus), -is_default (other.is_default), +has_default (other.has_default), is_external_function (other.is_external_function) { // guard to prevent null dereference (always required) @@ -1100,7 +1100,7 @@ Function::operator= (Function const &other) // visibility = other.visibility->clone_visibility(); // outer_attrs = other.outer_attrs; locus = other.locus; - is_default = other.is_default; + has_default = other.has_default; is_external_function = other.is_external_function; // guard to prevent null dereference (always required) diff --git a/gcc/rust/ast/rust-item.h b/gcc/rust/ast/rust-item.h index 8eb0cc51d5db..3bfa30918fa8 100644 --- a/gcc/rust/ast/rust-item.h +++ b/gcc/rust/ast/rust-item.h @@ -1330,7 +1330,7 @@ class Function : public VisItem, public AssociatedItem, public ExternalItem WhereClause where_clause; tl::optional> function_body; location_t locus; - bool is_default; + bool has_default; bool is_external_function; public: @@ -1355,6 +1355,8 @@ public: bool has_body () const { return function_body.has_value (); } + bool is_default () const { return has_default; } + // Mega-constructor with all possible fields Function (Identifier function_name, FunctionQualifiers qualifiers, std::vector> generic_params, @@ -1362,7 +1364,7 @@ public: std::unique_ptr return_type, WhereClause where_clause, tl::optional> function_body, Visibility vis, std::vector outer_attrs, - location_t locus, bool is_default = false, + location_t locus, bool has_default = false, bool is_external_function = false) : VisItem (std::move (vis), std::move (outer_attrs)), ExternalItem (Stmt::node_id), qualifiers (std::move (qualifiers)), @@ -1372,7 +1374,7 @@ public: return_type (std::move (return_type)), where_clause (std::move (where_clause)), function_body (std::move (function_body)), locus (locus), - is_default (is_default), is_external_function (is_external_function) + has_default (has_default), is_external_function (is_external_function) {} // TODO: add constructor with less fields diff --git a/gcc/rust/hir/rust-ast-lower-implitem.cc b/gcc/rust/hir/rust-ast-lower-implitem.cc index 5380d255c563..c34be898d038 100644 --- a/gcc/rust/hir/rust-ast-lower-implitem.cc +++ b/gcc/rust/hir/rust-ast-lower-implitem.cc @@ -22,6 +22,7 @@ #include "rust-ast-lower-expr.h" #include "rust-ast-lower-pattern.h" #include "rust-ast-lower-block.h" +#include "rust-hir-item.h" #include "rust-item.h" namespace Rust { @@ -140,6 +141,9 @@ ASTLowerImplItem::visit (AST::Function &function) ASTLoweringType::translate (function.get_return_type ())) : nullptr; + Defaultness defaultness += function.is_default () ? Defaultness::Default : Defaultness::Final; + std::vector function_params; for (auto &p : function.get_function_params ()) { @@ -183,7 +187,7 @@ ASTLowerImplItem::visit (AST::Func
[gcc r15-9313] c++: self-dependent alias template [PR117530]
https://gcc.gnu.org/g:d034c78c7be613db3c25fddec1dd50222327117b commit r15-9313-gd034c78c7be613db3c25fddec1dd50222327117b Author: Jason Merrill Date: Mon Apr 7 14:35:14 2025 -0400 c++: self-dependent alias template [PR117530] Here, instantiating B means instantiating A, which means instantiating B. And then when we go to register the initial instantiation, it conflicts with the inner one. Fixed by checking after tsubst whether there's already something in the hash table. We already did something much like this in tsubst_decl, but that doesn't handle this case. While I was here, I noticed that we had a pop_deferring_access_checks on one early exit but not another, and since I wanted to add yet another I switched to using deferring_access_check_sentinel. PR c++/117530 gcc/cp/ChangeLog: * pt.cc (instantiate_template): Check retrieve_specialization after tsubst. gcc/testsuite/ChangeLog: * g++.dg/cpp2a/lambda-uneval27.C: New test. Diff: --- gcc/cp/pt.cc | 14 -- gcc/testsuite/g++.dg/cpp2a/lambda-uneval27.C | 10 ++ 2 files changed, 18 insertions(+), 6 deletions(-) diff --git a/gcc/cp/pt.cc b/gcc/cp/pt.cc index 95b89f1281ba..8f35fa702a21 100644 --- a/gcc/cp/pt.cc +++ b/gcc/cp/pt.cc @@ -22675,7 +22675,7 @@ instantiate_template (tree tmpl, tree orig_args, tsubst_flags_t complain) FUNCTION_DECL which is the desired context for access checking is not built yet. We solve this chicken-and-egg problem by deferring all checks until we have the FUNCTION_DECL. */ - push_deferring_access_checks (dk_deferred); + deferring_access_check_sentinel dacs (dk_deferred); /* Instantiation of the function happens in the context of the function template, not the context of the overload resolution we're doing. */ @@ -22733,10 +22733,13 @@ instantiate_template (tree tmpl, tree orig_args, tsubst_flags_t complain) pop_from_top_level (); if (fndecl == error_mark_node) -{ - pop_deferring_access_checks (); - return error_mark_node; -} +return error_mark_node; + + /* Substituting the type might have recursively instantiated this + same alias (c++/117530). */ + if (DECL_ALIAS_TEMPLATE_P (gen_tmpl) + && (spec = retrieve_specialization (gen_tmpl, targ_ptr, hash))) +return spec; /* The DECL_TI_TEMPLATE should always be the immediate parent template, not the most general template. */ @@ -22771,7 +22774,6 @@ instantiate_template (tree tmpl, tree orig_args, tsubst_flags_t complain) access_ok = false; pop_access_scope (fndecl); } - pop_deferring_access_checks (); /* If we've just instantiated the main entry point for a function, instantiate all the alternate entry points as well. We do this diff --git a/gcc/testsuite/g++.dg/cpp2a/lambda-uneval27.C b/gcc/testsuite/g++.dg/cpp2a/lambda-uneval27.C new file mode 100644 index ..941fe636f6d5 --- /dev/null +++ b/gcc/testsuite/g++.dg/cpp2a/lambda-uneval27.C @@ -0,0 +1,10 @@ +// PR c++/117530 +// { dg-do compile { target c++20 } } + +template struct A; +template using B = decltype([]() -> A::X { return 0; }); +template struct A { + typedef int X; + typedef B U; +}; +B b;
[gcc/devel/rust/master] Update ast visitor with proper check for looplabel
https://gcc.gnu.org/g:8a65b913d4c4f00c2b8aa6827c733786e4a0266e commit 8a65b913d4c4f00c2b8aa6827c733786e4a0266e Author: Pierre-Emmanuel Patry Date: Tue Apr 1 16:10:38 2025 +0200 Update ast visitor with proper check for looplabel The visitor was visiting loop label even when they did not exist. gcc/rust/ChangeLog: * ast/rust-ast-visitor.cc (DefaultASTVisitor::visit): Add check for loop label before visiting it. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/rust/ast/rust-ast-visitor.cc | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/gcc/rust/ast/rust-ast-visitor.cc b/gcc/rust/ast/rust-ast-visitor.cc index 7791489a1667..3a06d2ddc4b7 100644 --- a/gcc/rust/ast/rust-ast-visitor.cc +++ b/gcc/rust/ast/rust-ast-visitor.cc @@ -559,7 +559,8 @@ void DefaultASTVisitor::visit (AST::LoopExpr &expr) { visit_outer_attrs (expr); - visit (expr.get_loop_label ()); + if (expr.has_loop_label ()) +visit (expr.get_loop_label ()); visit (expr.get_loop_block ()); }
[gcc/devel/rust/master] Visit loop label before predicate expression
https://gcc.gnu.org/g:b079d612f685de0d7780837bae5bfe88ce46ccbe commit b079d612f685de0d7780837bae5bfe88ce46ccbe Author: Pierre-Emmanuel Patry Date: Tue Apr 1 12:02:31 2025 +0200 Visit loop label before predicate expression If the label is referenced within the while predicate expression it has to be resolved before the latter. gcc/rust/ChangeLog: * ast/rust-ast-visitor.cc (DefaultASTVisitor::visit): Change default visit order. gcc/testsuite/ChangeLog: * rust/compile/nr2/exclude: Remove test from exclusion list. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/rust/ast/rust-ast-visitor.cc | 2 +- gcc/testsuite/rust/compile/nr2/exclude | 2 -- 2 files changed, 1 insertion(+), 3 deletions(-) diff --git a/gcc/rust/ast/rust-ast-visitor.cc b/gcc/rust/ast/rust-ast-visitor.cc index b5da001da5ac..7791489a1667 100644 --- a/gcc/rust/ast/rust-ast-visitor.cc +++ b/gcc/rust/ast/rust-ast-visitor.cc @@ -567,9 +567,9 @@ void DefaultASTVisitor::visit (AST::WhileLoopExpr &expr) { visit_outer_attrs (expr); - visit (expr.get_predicate_expr ()); if (expr.has_loop_label ()) visit (expr.get_loop_label ()); + visit (expr.get_predicate_expr ()); visit (expr.get_loop_block ()); } diff --git a/gcc/testsuite/rust/compile/nr2/exclude b/gcc/testsuite/rust/compile/nr2/exclude index 2f4585cbe8c4..c688026a7b8f 100644 --- a/gcc/testsuite/rust/compile/nr2/exclude +++ b/gcc/testsuite/rust/compile/nr2/exclude @@ -14,9 +14,7 @@ pub_restricted_2.rs pub_restricted_3.rs undeclared_label.rs use_1.rs -while_break_expr.rs issue-2905-2.rs -issue-266.rs derive_clone_enum3.rs derive-debug1.rs derive-default1.rs
[gcc r13-9497] ipa-cp: Avoid ICE when redistributing nodes among edges to recursive clones (PR 118318)
https://gcc.gnu.org/g:659e222b82c41ae0730a0bb93d891864b6ae5e16 commit r13-9497-g659e222b82c41ae0730a0bb93d891864b6ae5e16 Author: Martin Jambor Date: Fri Mar 7 17:17:24 2025 +0100 ipa-cp: Avoid ICE when redistributing nodes among edges to recursive clones (PR 118318) PR 118318 reported an ICE during PGO build of Firefox when IPA-CP, in the final stages of update_counts_for_self_gen_clones where it attempts to guess how to distribute profile count among clones created for recursive edges and the various edges that are created in the process. If one such edge has profile count of kind GUESSED_GLOBAL0, the compatibility check in the operator+ will lead to an ICE. After discussing the situation with Honza, we concluded that there is little more we can do other than check for this situation before touching the edge count, so this is what this patch does. gcc/ChangeLog: 2025-02-28 Martin Jambor PR ipa/118318 * ipa-cp.cc (adjust_clone_incoming_counts): Add a compatible_p check. (cherry picked from commit 7deb498425799aceb7659ea25614175a49533184) Diff: --- gcc/ipa-cp.cc | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/gcc/ipa-cp.cc b/gcc/ipa-cp.cc index 8f36608cf33b..08fca00e5f65 100644 --- a/gcc/ipa-cp.cc +++ b/gcc/ipa-cp.cc @@ -4808,7 +4808,8 @@ adjust_clone_incoming_counts (cgraph_node *node, cs->count = cs->count.combine_with_ipa_count (sum); } else if (!desc->processed_edges->contains (cs) -&& cs->caller->clone_of == desc->orig) +&& cs->caller->clone_of == desc->orig +&& cs->count.compatible_p (desc->count)) { cs->count += desc->count; if (dump_file)
[gcc/devel/omp/gcc-14] OpenMP: Fix append_args handling in modify_call_for_omp_dispatch
https://gcc.gnu.org/g:e14ab294c02ff6a1c63aee447d4cc47b74462d1a commit e14ab294c02ff6a1c63aee447d4cc47b74462d1a Author: Tobias Burnus Date: Tue Apr 8 13:47:53 2025 +0200 OpenMP: Fix append_args handling in modify_call_for_omp_dispatch At tree level, the addr ref is also required for array dummy arguments, contrary to C; the GOMP_interop calls in modify_call_for_omp_dispatch were updated accordingly (using build_fold_addr_expr). As the GOMP_interop calls had no location data associated with them, the init call happened as soon as executing the previous line of code, which was confusing; solution: use the location data of the function call itself. PR middle-end/119662 gcc/ChangeLog: * gimplify.cc (modify_call_for_omp_dispatch): Fix GOMP_interop arg passing; add location info to function calls. libgomp/ChangeLog: * testsuite/libgomp.c/append-args-fr-1.c: New test. * testsuite/libgomp.c/append-args-fr.h: New test. gcc/testsuite/ChangeLog: * c-c++-common/gomp/append-args-interop.c: Update for fixed GOMP_interop call. * g++.dg/gomp/append-args-8.C: Likewise. * gfortran.dg/gomp/append-args-interop.f90: Likewise. (cherry picked from commit 0f77d88fdf797842ac0134a4013b4227dd5a658f) Diff: --- gcc/ChangeLog.omp | 9 + gcc/gimplify.cc| 32 ++- gcc/testsuite/ChangeLog.omp| 11 + .../c-c++-common/gomp/append-args-interop.c| 4 +- gcc/testsuite/g++.dg/gomp/append-args-8.C | 8 +- .../gfortran.dg/gomp/append-args-interop.f90 | 4 +- libgomp/ChangeLog.omp | 9 + libgomp/testsuite/libgomp.c/append-args-fr-1.c | 232 libgomp/testsuite/libgomp.c/append-args-fr.h | 306 + 9 files changed, 593 insertions(+), 22 deletions(-) diff --git a/gcc/ChangeLog.omp b/gcc/ChangeLog.omp index b4c19fc4c377..0ffb30b66c04 100644 --- a/gcc/ChangeLog.omp +++ b/gcc/ChangeLog.omp @@ -1,3 +1,12 @@ +2025-04-08 Tobias Burnus + + Backported from master: + 2025-04-08 Tobias Burnus + + PR middle-end/119662 + * gimplify.cc (modify_call_for_omp_dispatch): Fix GOMP_interop + arg passing; add location info to function calls. + 2025-04-02 Thomas Schwinge Backported from trunk: diff --git a/gcc/gimplify.cc b/gcc/gimplify.cc index 57f49be4fbb3..0319a0b64dd8 100644 --- a/gcc/gimplify.cc +++ b/gcc/gimplify.cc @@ -3907,6 +3907,7 @@ static tree modify_call_for_omp_dispatch (tree expr, tree dispatch_clauses, bool want_value, bool pointerize) { + location_t loc = EXPR_LOCATION (expr); tree fndecl = get_callee_fndecl (expr); /* Skip processing if we don't get the expected call form. */ @@ -4101,14 +4102,17 @@ modify_call_for_omp_dispatch (tree expr, tree dispatch_clauses, } } + objs = build_fold_addr_expr (objs); + target_tgtsync = build_fold_addr_expr (target_tgtsync); + prefer_type = prefer_type ? build_fold_addr_expr (prefer_type) + : null_pointer_node; tree fn = builtin_decl_explicit (BUILT_IN_GOMP_INTEROP); tree create - = build_call_expr (fn, 11, dispatch_device_num, - nobjs, objs, target_tgtsync, - prefer_type ? prefer_type : null_pointer_node, - integer_zero_node, null_pointer_node, - integer_zero_node, null_pointer_node, - integer_zero_node, null_pointer_node); + = build_call_expr_loc (loc, fn, 11, dispatch_device_num, + nobjs, objs, target_tgtsync, prefer_type, + integer_zero_node, null_pointer_node, + integer_zero_node, null_pointer_node, + integer_zero_node, null_pointer_node); if (init_code) init_code = build2 (COMPOUND_EXPR, TREE_TYPE (create), init_code, create); @@ -4116,12 +4120,12 @@ modify_call_for_omp_dispatch (tree expr, tree dispatch_clauses, init_code = create; cleanup - = build_call_expr (fn, 11, dispatch_device_num, - integer_zero_node, null_pointer_node, - null_pointer_node, null_pointer_node, - integer_zero_node, null_pointer_node, - nobjs, objs, - integer_zero_node, null_pointer_node); + = build_call_expr_loc (loc, fn, 11, dispatch_device_num, + integer_zero_node, null_pointe
[gcc/devel/omp/gcc-14] Merge remote-tracking branch 'origin/releases/gcc-14' into devel/omp/gcc-14
https://gcc.gnu.org/g:b25ca248132a79766ea6f1e8c5b9bd691ba399f3 commit b25ca248132a79766ea6f1e8c5b9bd691ba399f3 Merge: e14ab294c02f 059107eb22c4 Author: Tobias Burnus Date: Tue Apr 8 23:51:05 2025 +0200 Merge remote-tracking branch 'origin/releases/gcc-14' into devel/omp/gcc-14 Merge up to r14-11542-g059107eb22c480 (8th Apr 2025) Diff: gcc/ChangeLog | 361 + gcc/DATESTAMP |2 +- gcc/ada/ChangeLog | 12 + gcc/ada/libgnat/a-ngcoar.adb | 42 +- gcc/ada/libgnat/a-ngrear.adb | 85 +- gcc/builtins.cc| 21 +- gcc/c-family/ChangeLog | 11 + gcc/c-family/c-pretty-print.cc |6 +- gcc/c/ChangeLog| 80 + gcc/c/c-decl.cc| 123 +- gcc/c/c-objc-common.h |2 + gcc/c/c-parser.cc | 24 +- gcc/c/c-tree.h | 21 +- gcc/c/c-typeck.cc | 375 - gcc/cgraph.cc |7 +- gcc/common/config/i386/i386-isas.h |1 + gcc/config/aarch64/aarch64.cc |6 +- gcc/config/aarch64/aarch64.md |8 +- gcc/config/avr/avr-mcus.def|6 + gcc/config/i386/i386-c.cc |5 +- gcc/config/i386/i386-options.cc|1 + gcc/config/i386/i386.md|4 +- gcc/config/i386/i386.opt |5 + gcc/config/i386/i386.opt.urls |3 + gcc/config/loongarch/loongarch.cc | 13 + gcc/cp/ChangeLog | 128 ++ gcc/cp/call.cc | 14 +- gcc/cp/constexpr.cc| 38 +- gcc/cp/cp-tree.h |1 + gcc/cp/cvt.cc | 13 + gcc/cp/lambda.cc |8 +- gcc/cp/name-lookup.cc | 11 +- gcc/cp/parser.cc | 98 +- gcc/cp/pt.cc |2 + gcc/cp/rtti.cc |3 +- gcc/cp/semantics.cc|1 + gcc/cp/typeck.cc | 10 +- gcc/d/ChangeLog| 20 + gcc/d/decl.cc |6 + gcc/d/expr.cc |2 + gcc/d/types.cc |5 +- gcc/df-problems.cc |8 +- gcc/doc/avr-mmcu.texi |4 +- gcc/doc/extend.texi|8 +- gcc/doc/invoke.texi|4 +- gcc/doc/sourcebuild.texi |3 + gcc/dwarf2out.cc |6 +- gcc/fortran/ChangeLog | 23 + gcc/fortran/resolve.cc |2 +- gcc/fortran/trans-array.cc |8 +- gcc/gimplify.cc|8 +- gcc/ginclude/stddef.h |8 +- gcc/ipa-cp.cc |3 +- gcc/ipa-devirt.cc | 10 +- gcc/ipa-free-lang-data.cc | 14 + gcc/ipa-modref.cc |3 +- gcc/lra-constraints.cc |3 +- gcc/lto/ChangeLog | 27 + gcc/lto/lto-common.cc |9 +- gcc/lto/lto-symtab.cc |2 +- gcc/omp-simd-clone.cc |2 +- gcc/testsuite/ChangeLog| 406 + gcc/testsuite/c-c++-common/gomp/pr119000.c | 16 + .../g++.dg/cpp0x/lambda/lambda-__func__3.C |6 + gcc/testsuite/g++.dg/cpp0x/pr119123.C | 10 + gcc/testsuite/g++.dg/cpp0x/pr98533.C | 25 + gcc/testsuite/g++.dg/cpp0x/temp-extend3.C | 32 + gcc/testsuite/g++.dg/cpp1y/constexpr-complex2.C| 18 + gcc/testsuite/g++.dg/cpp2a/concepts-pr116681.C | 20 + gcc/testsuite/g++.dg/cpp2a/concepts-requires41.C | 25 + gcc/testsuite/g++.dg/cpp2a/consteval41.C | 37 + gcc/testsuite/g++.dg/cpp2a/constexpr-117504.C | 60 + gcc/testsuite/g++.dg/cpp2a/constexpr-117504a.C | 12 + gcc/testsuite/g++.dg/cpp2a/constinit20.C | 18 + gcc/testsuite/g++.dg/cpp2a/lambda-requires2.C |8 + gcc/testsuite/g+
[gcc/devel/omp/gcc-14] (112 commits) Merge remote-tracking branch 'origin/releases/gcc-14' into
The branch 'devel/omp/gcc-14' was updated to point to: b25ca248132a... Merge remote-tracking branch 'origin/releases/gcc-14' into It previously pointed to: be92d54c5622... OpenMP: Require target and/or targetsync init modifier [PR1 Diff: Summary of changes (added commits): --- b25ca24... Merge remote-tracking branch 'origin/releases/gcc-14' into e14ab29... OpenMP: Fix append_args handling in modify_call_for_omp_dis 059107e... libstdc++: Fix use-after-free in std::format [PR119671] (*) 7e789f3... libstdc++: Add new header to Doxygen config file (*) 7ad64ff... libstdc++: Replace use of __mindist in ranges::uninitialize (*) ef11c15... libstdc++: Replace use of std::min in ranges::uninitialized (*) 73a6237... LoongArch: Add LoongArch architecture detection to __float1 (*) da91ea5... Daily bump. (*) 5cdf31f... libstdc++: Work around C++20 tuple> constraint r (*) 749221f... c++: constinit and value-initialization [PR119652] (*) e2a178a... c++: __FUNCTION__ in lambda return type [PR118629] (*) 2e58e23... Daily bump. (*) cfd1652... Daily bump. (*) 4feaf39... Daily bump. (*) ecc2725... c++: lambda in requires outside template [PR99546] (*) 49b6308... c++: constraint variable used in evaluated context [PR11784 (*) 9a74709... c++: P2280R4 and speculative constexpr folding [PR119387] (*) a210011... Ada: Fix thinko in Eigensystem for complex Hermitian matric (*) 2b9a842... vect: Relax scan-tree-dump strict pattern matching [PR11859 (*) 370f054... Daily bump. (*) 83cd4bd... libstdc++: Restored accidentally removed test case. (*) ad1b71f... libstdc++: Fix handling of field width for wide strings and (*) f955c5b... Fortran: Fix freeing procedure pointer components [PR119380 (*) 1fb3a8d... Daily bump. (*) 534a789... tree-optimization/119145 - avoid stray .MASK_CALL after vec (*) 2f87983... middle-end/119119 - re-gimplification of empty CTOR assignm (*) d3e4c09... tree-optimization/119096 - bogus conditional reduction vect (*) 85ed633... ipa/119067 - bogus TYPE_PRECISION check on VECTOR_TYPE (*) faadd1d... tree-optimization/119057 - bogus double reduction detection (*) ed7f67d... lto/114501 - missed free-lang-data for CONSTRUCTOR index (*) d9faa7c... ipa/111245 - bogus modref analysis for store in call that m (*) 35ed15a... aarch64: Use PAUTH instead of V8_3A in some places (*) 88f0c1f... libstdc++: Fix std::ranges::iter_move for function referenc (*) 58a2b7f... libstdc++: Fix ranges::iter_move handling of rvalues [PR106 (*) 9d5baaa... libstdc++: Fix -Warray-bounds warning in std::vector (*) f0c4ffc... libstdc++: Fix -Wstringop-overread warning in std::vector [PR119429] (*) b5d04ff... libstdc++: Define operator== for hash table iterators [PR11 (*) f8c281d... Daily bump. (*) de9500d... Fortran: fix bogus bounds check for reallocation on assignm (*) 82bd831... ipa-cp: Avoid ICE when redistributing nodes among edges to (*) 925a744... libstdc++: Fix ref_view branch of views::as_const [PR119135 (*) f078a61... c++: Don't replace INDIRECT_REFs by a const capture proxy t (*) 96be983... Daily bump. (*) 5ba6fdc... i386: Add -mavx10.1 back with 512 bit alias (*) 8bac228... c++: Don't mix timevar_start and auto_cond_timevar for TV_N (*) 2ba7823... Daily bump. (*) 18f6f54... AVR: Add AVR-SD devices. (*) e4e7d44... d: Fix ICE type variant differs by TYPE_PACKED [PR117621] (*) bfcf402... Daily bump. (*) a3989d8... c: Set attributes for fields when forming a composite type (*) 432f918... c: minor fixes related to arrays of unspecified size (*) 9d9dc4b... c: detect variably-modified types [PR117145,PR117245,PR1004 (*) d025b68... c++: ICE w/ dependently scoped template friend [PR119378] (*) 9c0c533... Daily bump. (*) (*) This commit already exists in another branch. Because the reference `refs/heads/devel/omp/gcc-14' matches your hooks.email-new-commits-only configuration, no separate email is sent for this commit.
[gcc r14-11539] libstdc++: Replace use of std::min in ranges::uninitialized_xxx algos [PR101587]
https://gcc.gnu.org/g:ef11c1573d16db756c246ac029a99947bdc01aa3 commit r14-11539-gef11c1573d16db756c246ac029a99947bdc01aa3 Author: Jonathan Wakely Date: Wed Mar 26 11:47:05 2025 + libstdc++: Replace use of std::min in ranges::uninitialized_xxx algos [PR101587] Because ranges can have any signed integer-like type as difference_type, it's not valid to use std::min(diff1, diff2). Instead of calling std::min with an explicit template argument, this adds a new __mindist helper that determines the common type and uses that with std::min. libstdc++-v3/ChangeLog: PR libstdc++/101587 * include/bits/ranges_uninitialized.h (__detail::__mindist): New function object. (ranges::uninitialized_copy, ranges::uninitialized_copy_n) (ranges::uninitialized_move, ranges::uninitialized_move_n): Use __mindist instead of std::min. * testsuite/20_util/specialized_algorithms/uninitialized_copy/constrained.cc: Check ranges with difference difference types. * testsuite/20_util/specialized_algorithms/uninitialized_move/constrained.cc: Likewise. (cherry picked from commit f4b6acfc36fb1f72fdd5bf4da208515e6495a062) Diff: --- libstdc++-v3/include/bits/ranges_uninitialized.h | 32 ++ .../uninitialized_copy/constrained.cc | 13 + .../uninitialized_move/constrained.cc | 13 + 3 files changed, 52 insertions(+), 6 deletions(-) diff --git a/libstdc++-v3/include/bits/ranges_uninitialized.h b/libstdc++-v3/include/bits/ranges_uninitialized.h index f16f2ef39f59..99a11f0fa7cc 100644 --- a/libstdc++-v3/include/bits/ranges_uninitialized.h +++ b/libstdc++-v3/include/bits/ranges_uninitialized.h @@ -252,6 +252,26 @@ namespace ranges inline constexpr __uninitialized_value_construct_n_fn uninitialized_value_construct_n; + namespace __detail + { +// This is only intended for finding smaller iterator differences below, +// not as a general purpose replacement for std::min. +struct __mindist_fn +{ + template + constexpr common_type_t<_Dp1, _Dp2> + operator()(_Dp1 __d1, _Dp2 __d2) const noexcept + { + // Every C++20 iterator I satisfies weakly_incrementable which + // requires signed-integer-like>. + static_assert(std::__detail::__is_signed_integer_like<_Dp1>); + static_assert(std::__detail::__is_signed_integer_like<_Dp2>); + return std::min>(__d1, __d2); + } +}; +inline constexpr __mindist_fn __mindist{}; + } + template using uninitialized_copy_result = in_out_result<_Iter, _Out>; @@ -274,8 +294,8 @@ namespace ranges { auto __d1 = __ilast - __ifirst; auto __d2 = __olast - __ofirst; - return ranges::copy_n(std::move(__ifirst), std::min(__d1, __d2), - __ofirst); + return ranges::copy_n(std::move(__ifirst), + __detail::__mindist(__d1, __d2), __ofirst); } else { @@ -321,8 +341,8 @@ namespace ranges iter_reference_t<_Iter>>) { auto __d = __olast - __ofirst; - return ranges::copy_n(std::move(__ifirst), std::min(__n, __d), - __ofirst); + return ranges::copy_n(std::move(__ifirst), + __detail::__mindist(__n, __d), __ofirst); } else { @@ -363,7 +383,7 @@ namespace ranges auto __d2 = __olast - __ofirst; auto [__in, __out] = ranges::copy_n(std::make_move_iterator(std::move(__ifirst)), - std::min(__d1, __d2), __ofirst); + __detail::__mindist(__d1, __d2), __ofirst); return {std::move(__in).base(), __out}; } else @@ -414,7 +434,7 @@ namespace ranges auto __d = __olast - __ofirst; auto [__in, __out] = ranges::copy_n(std::make_move_iterator(std::move(__ifirst)), - std::min(__n, __d), __ofirst); + __detail::__mindist(__n, __d), __ofirst); return {std::move(__in).base(), __out}; } else diff --git a/libstdc++-v3/testsuite/20_util/specialized_algorithms/uninitialized_copy/constrained.cc b/libstdc++-v3/testsuite/20_util/specialized_algorithms/uninitialized_copy/constrained.cc index 79cf7afb29c9..a28b0607e925 100644 --- a/libstdc++-v3/testsuite/20_util/specialized_algorithms/uninitialized_copy/constrained.cc +++ b/libstdc++-v3/testsuite/20_util/specialized_algorithms/uninitialized_copy/constrained.cc @@ -175,6 +175,17 @@ test03() } } +void +test_pr101587() +{ + short in[1]; + __gnu_test::test_contiguous_range r(in); // difference_type is inte
[gcc r15-9325] c++: lambda in concept [PR118698]
https://gcc.gnu.org/g:94438ca82792063abf05823326695af25ab02d17 commit r15-9325-g94438ca82792063abf05823326695af25ab02d17 Author: Jason Merrill Date: Tue Apr 8 15:53:34 2025 -0400 c++: lambda in concept [PR118698] When normalizing is_foo for , we get to normalizing callable for , which means substituting into . Since r14-9938, because in_template_context is false we return the lambda unchanged, just with LAMBDA_EXPR_EXTRA_ARGS set, so the closure type still refers to the is_specialization_of tparms in its CLASSTYPE_TEMPLATE_INFO. So then in normalize_atom caching find_template_parameters walks over the parameter mapping; any_template_parm_r walks into the TREE_TYPE of a LAMBDA_EXPR without considering EXTRA_ARGS and finds a template parm from the wrong parameter list. But since r15-3530 we expect to set tf_partial when substituting with dependent arguments, so we should set that when normalizing. And then tf_partial causes TREE_STATIC to be set on the EXTRA_ARGS, meaning that those args will replace all the template parms in the rest of the lambda, so we can walk just the EXTRA_ARGS and ignore the rest. PR c++/118698 gcc/cp/ChangeLog: * constraint.cc (struct norm_info): Add tf_partial. * pt.cc (any_template_parm_r): Handle LAMBDA_EXPR_EXTRA_ARGS. gcc/testsuite/ChangeLog: * g++.dg/cpp2a/concepts-lambda22.C: New test. Diff: --- gcc/cp/constraint.cc | 2 +- gcc/cp/pt.cc | 12 gcc/testsuite/g++.dg/cpp2a/concepts-lambda22.C | 21 + 3 files changed, 34 insertions(+), 1 deletion(-) diff --git a/gcc/cp/constraint.cc b/gcc/cp/constraint.cc index a9caba8e2cc7..2f1678ce4ff9 100644 --- a/gcc/cp/constraint.cc +++ b/gcc/cp/constraint.cc @@ -354,7 +354,7 @@ struct norm_info : subst_info /* Construct a top-level context for DECL. */ norm_info (tree in_decl, bool diag) -: subst_info (tf_warning_or_error, in_decl), +: subst_info (tf_warning_or_error|tf_partial, in_decl), generate_diagnostics (diag) { if (in_decl) diff --git a/gcc/cp/pt.cc b/gcc/cp/pt.cc index 8f35fa702a21..0e120c4040ed 100644 --- a/gcc/cp/pt.cc +++ b/gcc/cp/pt.cc @@ -7,6 +7,18 @@ any_template_parm_r (tree t, void *data) case LAMBDA_EXPR: { + /* TREE_STATIC on LAMBDA_EXPR_EXTRA_ARGS means a full set of + arguments, so we can just look there; they will replace + any template parms in the rest of the LAMBDA_EXPR. */ + if (tree args = LAMBDA_EXPR_EXTRA_ARGS (t)) + { + WALK_SUBTREE (args); + /* Without TREE_STATIC the args are just outer levels, so we'd + still need to look through the lambda for just inner + parameters. Hopefully that's not necessary. */ + gcc_checking_assert (TREE_STATIC (args)); + return 0; + } /* Look in the parms and body. */ tree fn = lambda_function (t); WALK_SUBTREE (TREE_TYPE (fn)); diff --git a/gcc/testsuite/g++.dg/cpp2a/concepts-lambda22.C b/gcc/testsuite/g++.dg/cpp2a/concepts-lambda22.C new file mode 100644 index ..2437b7e06a94 --- /dev/null +++ b/gcc/testsuite/g++.dg/cpp2a/concepts-lambda22.C @@ -0,0 +1,21 @@ +// PR c++/118698 +// { dg-do compile { target c++20 } } + +template struct foo {}; +template struct bar {}; + +template T&& declval (); + +template +concept callable = requires { declval()(declval()); }; + +template typename U> +concept is_specialization_of = callable( U const& ) { }),T>; + +static_assert( is_specialization_of,foo> == true ); +static_assert( is_specialization_of,bar> == false ); + +template concept is_foo = is_specialization_of; + +static_assert( is_foo> ); +static_assert( is_foo> == false );
[gcc r15-9321] testsuite: Fix gcc.dg/vect/pr99102.c command line
https://gcc.gnu.org/g:c3e1c23e8bd80284c4b7206ec260bb273d86da22 commit r15-9321-gc3e1c23e8bd80284c4b7206ec260bb273d86da22 Author: Richard Sandiford Date: Tue Apr 8 22:03:39 2025 +0100 testsuite: Fix gcc.dg/vect/pr99102.c command line The aarch64_sve256_hw line forced the vector length, but didn't force SVE itself. This meant that the associated: /* { dg-final { scan-tree-dump "MASK_SCATTER_STORE" "vect" { target aarch64_sve256_hw } } } */ wouldn't always fire. I imagine this was tested with SVE enabled by default, which would have masked the problem. gcc/testsuite/ * gcc.dg/vect/pr99102.c: Force SVE when forcing the vector length. Diff: --- gcc/testsuite/gcc.dg/vect/pr99102.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gcc/testsuite/gcc.dg/vect/pr99102.c b/gcc/testsuite/gcc.dg/vect/pr99102.c index 071741f5e48a..fcbf03674027 100644 --- a/gcc/testsuite/gcc.dg/vect/pr99102.c +++ b/gcc/testsuite/gcc.dg/vect/pr99102.c @@ -1,5 +1,5 @@ /* { dg-additional-options "-O2 -ftree-vectorize -fno-vect-cost-model -fdump-tree-vect-details" } */ -/* { dg-additional-options "-msve-vector-bits=256" { target aarch64_sve256_hw } } */ +/* { dg-additional-options "-march=armv8-a+sve -msve-vector-bits=256" { target aarch64_sve256_hw } } */ long a[44]; short d, e = -7; __attribute__((noipa)) void b(char f, short j, short k, unsigned l) {
[gcc r15-9324] LoongArch: Fix awk / sed usage for compatibility
https://gcc.gnu.org/g:6ed8c17c2bce631ae370d93164ceb6c1b5adf925 commit r15-9324-g6ed8c17c2bce631ae370d93164ceb6c1b5adf925 Author: Yang Yujie Date: Mon Apr 7 10:31:46 2025 +0800 LoongArch: Fix awk / sed usage for compatibility Tested with nawk, mawk, and gawk. gcc/ChangeLog: * config/loongarch/genopts/gen-evolution.awk: remove usage of "asort". * config/loongarch/genopts/genstr.sh: replace sed with awk. Diff: --- gcc/config/loongarch/genopts/gen-evolution.awk | 12 +- gcc/config/loongarch/genopts/genstr.sh | 57 ++ 2 files changed, 40 insertions(+), 29 deletions(-) diff --git a/gcc/config/loongarch/genopts/gen-evolution.awk b/gcc/config/loongarch/genopts/gen-evolution.awk index 142b658fe7a3..507063bd50df 100644 --- a/gcc/config/loongarch/genopts/gen-evolution.awk +++ b/gcc/config/loongarch/genopts/gen-evolution.awk @@ -101,10 +101,18 @@ function gen_cpucfg_useful_idx() idx_list[j++] = i+0 delete idx_bucket -asort (idx_list) +for (i = 1; i < j; i++) { +t = i +for (k = i + 1; k < j; k++) +t = idx_list[k] < idx_list[t] ? k : t + +k = idx_list[t] +idx_list[t] = idx_list[i] +idx_list[i] = k +} print "static constexpr int cpucfg_useful_idx[] = {" -for (i in idx_list) +for (i = 1; i < j; i++) printf(" %d,\n", idx_list[i]) print "};" diff --git a/gcc/config/loongarch/genopts/genstr.sh b/gcc/config/loongarch/genopts/genstr.sh index 16c2edd4fa8a..97517da40f49 100755 --- a/gcc/config/loongarch/genopts/genstr.sh +++ b/gcc/config/loongarch/genopts/genstr.sh @@ -51,18 +51,18 @@ along with GCC; see the file COPYING3. If not see #define LOONGARCH_STR_H EOF -sed -e '/^$/n' -e 's@#.*$@@' -e '/^$/d' \ - -e 's@^\([^ \t]\+\)[ \t]*\([^ \t]*\)@#define \1 "\2"@' \ - loongarch-strings +awk '/^#.*$/ { next } /^$/ { print; next } + { printf ("#define %s \"%s\"\n", $1, $2) }' \ + loongarch-strings echo - # Generate the strings from isa-evolution.in. - awk '{ - a=$3 - gsub(/-/, "_", a) - print("#define OPTSTR_"toupper(a)"\t\""$3"\"") - }' isa-evolution.in +# Generate the strings from isa-evolution.in. +awk '{ + a=$3 + gsub(/-/, "_", a) + print("#define OPTSTR_"toupper(a)"\t\""$3"\"") +}' isa-evolution.in echo echo "#endif /* LOONGARCH_STR_H */" @@ -73,18 +73,8 @@ EOF # according to the key-value pairs defined in loongarch-strings. gen_options() { - -sed -e '/^$/n' -e 's@#.*$@@' -e '/^$/d' \ - -e 's@^\([^ \t]\+\)[ \t]*\([^ \t]*\)@\1="\2"@' \ - loongarch-strings | { \ - - # read the definitions - while read -r line; do - eval "$line" - done - - # print a header - cat << EOF +# print a header +cat << EOF ; Generated by "genstr" from the template "loongarch.opt.in" ; and definitions from "loongarch-strings" and "isa-evolution.in". ; @@ -95,12 +85,25 @@ gen_options() { ; EOF - # make the substitutions - sed -e 's@"@\\"@g' -e 's/@@\([^@]\+\)@@/${\1}/g' loongarch.opt.in | \ - while read -r line; do - eval "echo \"$line\"" - done -} +# Generate loongarch.opt. +awk 'BEGIN { +delete strtab +while (getline < "loongarch-strings" > 0) { +if ($0 ~ /^#.*$/ || $0 ~ /^$/) continue +strtab[$1] = $2 +} +} +{ +n = split($0, tmp, "@@") +for (i = 2; i <= n; i += 2) +tmp[i] = strtab[tmp[i]] + +for (i = 1; i <= n; i++) +printf("%s", tmp[i]) +printf ("\n") + +}' loongarch.opt.in + # Generate the strings from isa-evolution.in. awk '{
[gcc r13-9498] libstdc++: Replace use of std::min in ranges::uninitialized_xxx algos [PR101587]
https://gcc.gnu.org/g:b07ff1f34c0e74b7d812baa1bd5987ba2c8b9625 commit r13-9498-gb07ff1f34c0e74b7d812baa1bd5987ba2c8b9625 Author: Jonathan Wakely Date: Wed Mar 26 11:47:05 2025 + libstdc++: Replace use of std::min in ranges::uninitialized_xxx algos [PR101587] Because ranges can have any signed integer-like type as difference_type, it's not valid to use std::min(diff1, diff2). Instead of calling std::min with an explicit template argument, this adds a new __mindist helper that determines the common type and uses that with std::min. libstdc++-v3/ChangeLog: PR libstdc++/101587 * include/bits/ranges_uninitialized.h (__detail::__mindist): New function object. (ranges::uninitialized_copy, ranges::uninitialized_copy_n) (ranges::uninitialized_move, ranges::uninitialized_move_n): Use __mindist instead of std::min. * testsuite/20_util/specialized_algorithms/uninitialized_copy/constrained.cc: Check ranges with difference difference types. * testsuite/20_util/specialized_algorithms/uninitialized_move/constrained.cc: Likewise. (cherry picked from commit f4b6acfc36fb1f72fdd5bf4da208515e6495a062) Diff: --- libstdc++-v3/include/bits/ranges_uninitialized.h | 32 ++ .../uninitialized_copy/constrained.cc | 13 + .../uninitialized_move/constrained.cc | 13 + 3 files changed, 52 insertions(+), 6 deletions(-) diff --git a/libstdc++-v3/include/bits/ranges_uninitialized.h b/libstdc++-v3/include/bits/ranges_uninitialized.h index 386170d2a289..a77365a470a1 100644 --- a/libstdc++-v3/include/bits/ranges_uninitialized.h +++ b/libstdc++-v3/include/bits/ranges_uninitialized.h @@ -252,6 +252,26 @@ namespace ranges inline constexpr __uninitialized_value_construct_n_fn uninitialized_value_construct_n; + namespace __detail + { +// This is only intended for finding smaller iterator differences below, +// not as a general purpose replacement for std::min. +struct __mindist_fn +{ + template + constexpr common_type_t<_Dp1, _Dp2> + operator()(_Dp1 __d1, _Dp2 __d2) const noexcept + { + // Every C++20 iterator I satisfies weakly_incrementable which + // requires signed-integer-like>. + static_assert(std::__detail::__is_signed_integer_like<_Dp1>); + static_assert(std::__detail::__is_signed_integer_like<_Dp2>); + return std::min>(__d1, __d2); + } +}; +inline constexpr __mindist_fn __mindist{}; + } + template using uninitialized_copy_result = in_out_result<_Iter, _Out>; @@ -274,8 +294,8 @@ namespace ranges { auto __d1 = __ilast - __ifirst; auto __d2 = __olast - __ofirst; - return ranges::copy_n(std::move(__ifirst), std::min(__d1, __d2), - __ofirst); + return ranges::copy_n(std::move(__ifirst), + __detail::__mindist(__d1, __d2), __ofirst); } else { @@ -321,8 +341,8 @@ namespace ranges iter_reference_t<_Iter>>) { auto __d = __olast - __ofirst; - return ranges::copy_n(std::move(__ifirst), std::min(__n, __d), - __ofirst); + return ranges::copy_n(std::move(__ifirst), + __detail::__mindist(__n, __d), __ofirst); } else { @@ -363,7 +383,7 @@ namespace ranges auto __d2 = __olast - __ofirst; auto [__in, __out] = ranges::copy_n(std::make_move_iterator(std::move(__ifirst)), - std::min(__d1, __d2), __ofirst); + __detail::__mindist(__d1, __d2), __ofirst); return {std::move(__in).base(), __out}; } else @@ -414,7 +434,7 @@ namespace ranges auto __d = __olast - __ofirst; auto [__in, __out] = ranges::copy_n(std::make_move_iterator(std::move(__ifirst)), - std::min(__n, __d), __ofirst); + __detail::__mindist(__n, __d), __ofirst); return {std::move(__in).base(), __out}; } else diff --git a/libstdc++-v3/testsuite/20_util/specialized_algorithms/uninitialized_copy/constrained.cc b/libstdc++-v3/testsuite/20_util/specialized_algorithms/uninitialized_copy/constrained.cc index 9885d444768b..7cc9b2eb6a32 100644 --- a/libstdc++-v3/testsuite/20_util/specialized_algorithms/uninitialized_copy/constrained.cc +++ b/libstdc++-v3/testsuite/20_util/specialized_algorithms/uninitialized_copy/constrained.cc @@ -176,6 +176,17 @@ test03() } } +void +test_pr101587() +{ + short in[1]; + __gnu_test::test_contiguous_range r(in); // difference_type is integ
[gcc r13-9499] libstdc++: Replace use of __mindist in ranges::uninitialized_xxx algos [PR101587]
https://gcc.gnu.org/g:09584eb968ef4751a704ee6a79ac1f31fd7beec8 commit r13-9499-g09584eb968ef4751a704ee6a79ac1f31fd7beec8 Author: Jonathan Wakely Date: Wed Mar 26 11:47:05 2025 + libstdc++: Replace use of __mindist in ranges::uninitialized_xxx algos [PR101587] In r15-8980-gf4b6acfc36fb1f I introduced a new function object for finding the smaller of two distances. In bugzilla Hewill Kang pointed out that we still need to explicitly convert the result back to the right difference type, because the result might be an integer-like class type that doesn't convert to an integral type explicitly. Rather than doing that conversion in the __mindist function object, I think it's simpler to remove it again and just do a comparison and assignment. We always want the result to have a specific type, so we can just check if the value of the other type is smaller, and then convert that to the other type if so. libstdc++-v3/ChangeLog: PR libstdc++/101587 * include/bits/ranges_uninitialized.h (__detail::__mindist): Remove. (ranges::uninitialized_copy, ranges::uninitialized_copy_n) (ranges::uninitialized_move, ranges::uninitialized_move_n): Use comparison and assignment instead of __mindist. * testsuite/20_util/specialized_algorithms/uninitialized_copy/constrained.cc: Check with ranges that use integer-like class type for difference type. * testsuite/20_util/specialized_algorithms/uninitialized_move/constrained.cc: Likewise. Reviewed-by: Tomasz Kaminski Reviewed-by: Hewill Kang (cherry picked from commit 03ac8886e5c1fa16da90276fd721a57fa9435f4f) Diff: --- libstdc++-v3/include/bits/ranges_uninitialized.h | 46 +++--- .../uninitialized_copy/constrained.cc | 30 +- .../uninitialized_move/constrained.cc | 29 +- 3 files changed, 71 insertions(+), 34 deletions(-) diff --git a/libstdc++-v3/include/bits/ranges_uninitialized.h b/libstdc++-v3/include/bits/ranges_uninitialized.h index a77365a470a1..55a562121d27 100644 --- a/libstdc++-v3/include/bits/ranges_uninitialized.h +++ b/libstdc++-v3/include/bits/ranges_uninitialized.h @@ -252,26 +252,6 @@ namespace ranges inline constexpr __uninitialized_value_construct_n_fn uninitialized_value_construct_n; - namespace __detail - { -// This is only intended for finding smaller iterator differences below, -// not as a general purpose replacement for std::min. -struct __mindist_fn -{ - template - constexpr common_type_t<_Dp1, _Dp2> - operator()(_Dp1 __d1, _Dp2 __d2) const noexcept - { - // Every C++20 iterator I satisfies weakly_incrementable which - // requires signed-integer-like>. - static_assert(std::__detail::__is_signed_integer_like<_Dp1>); - static_assert(std::__detail::__is_signed_integer_like<_Dp2>); - return std::min>(__d1, __d2); - } -}; -inline constexpr __mindist_fn __mindist{}; - } - template using uninitialized_copy_result = in_out_result<_Iter, _Out>; @@ -292,10 +272,10 @@ namespace ranges && is_nothrow_assignable_v<_OutType&, iter_reference_t<_Iter>>) { - auto __d1 = __ilast - __ifirst; - auto __d2 = __olast - __ofirst; - return ranges::copy_n(std::move(__ifirst), - __detail::__mindist(__d1, __d2), __ofirst); + auto __d = __ilast - __ifirst; + if (auto __d2 = __olast - __ofirst; __d2 < __d) + __d = static_cast>(__d2); + return ranges::copy_n(std::move(__ifirst), __d, __ofirst); } else { @@ -340,9 +320,9 @@ namespace ranges && is_nothrow_assignable_v<_OutType&, iter_reference_t<_Iter>>) { - auto __d = __olast - __ofirst; - return ranges::copy_n(std::move(__ifirst), - __detail::__mindist(__n, __d), __ofirst); + if (auto __d = __olast - __ofirst; __d < __n) + __n = static_cast>(__d); + return ranges::copy_n(std::move(__ifirst), __n, __ofirst); } else { @@ -379,11 +359,12 @@ namespace ranges && is_nothrow_assignable_v<_OutType&, iter_rvalue_reference_t<_Iter>>) { - auto __d1 = __ilast - __ifirst; - auto __d2 = __olast - __ofirst; + auto __d = __ilast - __ifirst; + if (auto __d2 = __olast - __ofirst; __d2 < __d) + __d = static_cast>(__d2); auto [__in, __out] = ranges::copy_n(std::make_move_iterator(std::move(__ifirst))
[gcc r13-9500] libstdc++: Fix use-after-free in std::format [PR119671]
https://gcc.gnu.org/g:6c61f43b8cd410125026429a6ea87308dd49a786 commit r13-9500-g6c61f43b8cd410125026429a6ea87308dd49a786 Author: Jonathan Wakely Date: Mon Apr 7 19:52:55 2025 +0100 libstdc++: Fix use-after-free in std::format [PR119671] When formatting floating-point values to wide strings there's a case where we invalidate a std::wstring buffer while a std::wstring_view is still referring to it. libstdc++-v3/ChangeLog: PR libstdc++/119671 * include/std/format (__formatter_fp::format): Do not invalidate __wstr unless _M_localized returns a valid string. * testsuite/std/format/functions/format.cc: Check wide string formatting of floating-point types with classic locale. Reviewed-by: Tomasz Kaminski (cherry picked from commit e33b62eed7fd0a82d758b23252d288585b6790d2) Diff: --- libstdc++-v3/include/std/format | 9 + libstdc++-v3/testsuite/std/format/functions/format.cc | 12 2 files changed, 17 insertions(+), 4 deletions(-) diff --git a/libstdc++-v3/include/std/format b/libstdc++-v3/include/std/format index 26e87c427afd..f46012a2b014 100644 --- a/libstdc++-v3/include/std/format +++ b/libstdc++-v3/include/std/format @@ -1669,12 +1669,13 @@ namespace __format if (_M_spec._M_localized && __builtin_isfinite(__v)) { + basic_string<_CharT> __s; if constexpr (is_same_v) - __wstr = _M_localize(__str, __expc, __fc.locale()); + __s = _M_localize(__str, __expc, __fc.locale()); else - __wstr = _M_localize(__str, __expc, __loc.value()); - if (!__wstr.empty()) - __str = __wstr; + __s = _M_localize(__str, __expc, __loc.value()); + if (!__s.empty()) + __str = __wstr = std::move(__s); } size_t __width = _M_spec._M_get_width(__fc); diff --git a/libstdc++-v3/testsuite/std/format/functions/format.cc b/libstdc++-v3/testsuite/std/format/functions/format.cc index 16f5cda39f16..5d1d9ed07200 100644 --- a/libstdc++-v3/testsuite/std/format/functions/format.cc +++ b/libstdc++-v3/testsuite/std/format/functions/format.cc @@ -349,6 +349,18 @@ test_wchar() // P2909R4 Fix formatting of code units as integers (Dude, where’s my char?) s = std::format(L"{:d} {:d}", wchar_t(-1), char(-1)); VERIFY( s.find('-') == std::wstring::npos ); + + auto ws = std::format(L"{:L}", 0.5); + VERIFY( ws == L"0.5" ); + // The default C locale. + std::locale cloc = std::locale::classic(); + // PR libstdc++/119671 use-after-free formatting floating-point to wstring + ws = std::format(cloc, L"{:L}", 0.5); + VERIFY( ws == L"0.5" ); + // A locale with no name, but with the same facets as the C locale. + std::locale locx(cloc, &std::use_facet>(cloc)); + ws = std::format(locx, L"{:L}", 0.5); + VERIFY( ws == L"0.5" ); } void
[gcc r15-9319] libphobos: Merge with upstream phobos 35977c802
https://gcc.gnu.org/g:7767158577fd5a5cfdd9bf0c7ba8d47942d8940a commit r15-9319-g7767158577fd5a5cfdd9bf0c7ba8d47942d8940a Author: Iain Buclaw Date: Tue Apr 8 16:41:10 2025 +0200 libphobos: Merge with upstream phobos 35977c802 Synchronizes recent bug fixes targeted for v2.111.1. libphobos/ChangeLog: * src/MERGE: Merge upstream phobos 35977c802. * src/Makefile.am (PHOBOS_DSOURCES): Add std/internal/windows/bcrypt.d. * src/Makefile.in: Regenerate. Diff: --- libphobos/src/MERGE | 2 +- libphobos/src/Makefile.am | 17 libphobos/src/Makefile.in | 19 + libphobos/src/std/file.d| 4 +- libphobos/src/std/internal/windows/bcrypt.d | 65 + libphobos/src/std/random.d | 18 +--- 6 files changed, 89 insertions(+), 36 deletions(-) diff --git a/libphobos/src/MERGE b/libphobos/src/MERGE index 3dfe00877913..d870a91ba963 100644 --- a/libphobos/src/MERGE +++ b/libphobos/src/MERGE @@ -1,4 +1,4 @@ -60034b56e2a036a66fa78cbc0ec0290956423684 +35977c8029e7bb4dbe1b887688dabebe04ebea02 The first line of this file holds the git revision number of the last merge done from the dlang/phobos repository. diff --git a/libphobos/src/Makefile.am b/libphobos/src/Makefile.am index 94e28f3d175d..5d690dddf2bd 100644 --- a/libphobos/src/Makefile.am +++ b/libphobos/src/Makefile.am @@ -144,14 +144,15 @@ PHOBOS_DSOURCES = etc/c/curl.d etc/c/odbc/odbc32.d etc/c/odbc/odbc64.d \ std/internal/unicode_comp.d std/internal/unicode_decomp.d \ std/internal/unicode_grapheme.d std/internal/unicode_norm.d \ std/internal/unicode_tables.d std/internal/windows/advapi32.d \ - std/json.d std/logger/core.d std/logger/filelogger.d \ - std/logger/multilogger.d std/logger/nulllogger.d std/logger/package.d \ - std/math/algebraic.d std/math/constants.d std/math/exponential.d \ - std/math/hardware.d std/math/operations.d std/math/package.d \ - std/math/remainder.d std/math/rounding.d std/math/traits.d \ - std/math/trigonometry.d std/mathspecial.d std/meta.d std/mmfile.d \ - std/net/curl.d std/net/isemail.d std/numeric.d std/outbuffer.d \ - std/package.d std/parallelism.d std/path.d std/process.d std/random.d \ + std/internal/windows/bcrypt.d std/json.d std/logger/core.d \ + std/logger/filelogger.d std/logger/multilogger.d \ + std/logger/nulllogger.d std/logger/package.d std/math/algebraic.d \ + std/math/constants.d std/math/exponential.d std/math/hardware.d \ + std/math/operations.d std/math/package.d std/math/remainder.d \ + std/math/rounding.d std/math/traits.d std/math/trigonometry.d \ + std/mathspecial.d std/meta.d std/mmfile.d std/net/curl.d \ + std/net/isemail.d std/numeric.d std/outbuffer.d std/package.d \ + std/parallelism.d std/path.d std/process.d std/random.d \ std/range/interfaces.d std/range/package.d std/range/primitives.d \ std/regex/internal/backtracking.d std/regex/internal/generator.d \ std/regex/internal/ir.d std/regex/internal/kickstart.d \ diff --git a/libphobos/src/Makefile.in b/libphobos/src/Makefile.in index d052aa805c2c..2bf7e3f28747 100644 --- a/libphobos/src/Makefile.in +++ b/libphobos/src/Makefile.in @@ -252,6 +252,7 @@ am__dirstamp = $(am__leading_dot)dirstamp @ENABLE_LIBDRUNTIME_ONLY_FALSE@std/internal/unicode_norm.lo \ @ENABLE_LIBDRUNTIME_ONLY_FALSE@std/internal/unicode_tables.lo \ @ENABLE_LIBDRUNTIME_ONLY_FALSE@std/internal/windows/advapi32.lo \ +@ENABLE_LIBDRUNTIME_ONLY_FALSE@std/internal/windows/bcrypt.lo \ @ENABLE_LIBDRUNTIME_ONLY_FALSE@std/json.lo std/logger/core.lo \ @ENABLE_LIBDRUNTIME_ONLY_FALSE@std/logger/filelogger.lo \ @ENABLE_LIBDRUNTIME_ONLY_FALSE@std/logger/multilogger.lo \ @@ -612,14 +613,15 @@ libgphobos_la_LINK = $(LIBTOOL) --tag=D $(libgphobos_la_LIBTOOLFLAGS) \ @ENABLE_LIBDRUNTIME_ONLY_FALSE@std/internal/unicode_comp.d std/internal/unicode_decomp.d \ @ENABLE_LIBDRUNTIME_ONLY_FALSE@std/internal/unicode_grapheme.d std/internal/unicode_norm.d \ @ENABLE_LIBDRUNTIME_ONLY_FALSE@std/internal/unicode_tables.d std/internal/windows/advapi32.d \ -@ENABLE_LIBDRUNTIME_ONLY_FALSE@std/json.d std/logger/core.d std/logger/filelogger.d \ -@ENABLE_LIBDRUNTIME_ONLY_FALSE@std/logger/multilogger.d std/logger/nulllogger.d std/logger/package.d \ -@ENABLE_LIBDRUNTIME_ONLY_FALSE@std/math/algebraic.d std/math/constants.d std/math/exponential.d \ -@ENABLE_LIBDRUNTIME_ONLY_FALSE@std/math/hardware.d std/math/operations.d std/math/package.d \ -@ENABLE_LIBDRUNTIME_ONLY_FALSE@std/math/remainder.d std/math/rounding.d std/math/traits.d \ -@ENABLE_LIBDRUNTIME_ONLY_FALSE@std/math/trigonometry.d std/mathspecial.d std/meta.d std/mmfile.d \ -
[gcc r15-9318] d: Fix infinite loop in isAliasThisTuple
https://gcc.gnu.org/g:639376154eaffe683f4027c95a08c5d30922b12d commit r15-9318-g639376154eaffe683f4027c95a08c5d30922b12d Author: Iain Buclaw Date: Tue Apr 8 16:36:15 2025 +0200 d: Fix infinite loop in isAliasThisTuple This reverts a change in the upstream D implementation of the compiler, as the refactoring introduced a regression. gcc/d/ChangeLog: * dmd/MERGE: Merge upstream dmd 51816cd01d. Reviewed-on: https://github.com/dlang/dmd/pull/21155 Diff: --- gcc/d/dmd/MERGE | 2 +- gcc/d/dmd/expressionsem.d | 30 +++ gcc/testsuite/gdc.test/compilable/test21153.d | 8 +++ 3 files changed, 26 insertions(+), 14 deletions(-) diff --git a/gcc/d/dmd/MERGE b/gcc/d/dmd/MERGE index bd297b612c4e..a05a50eefb8d 100644 --- a/gcc/d/dmd/MERGE +++ b/gcc/d/dmd/MERGE @@ -1,4 +1,4 @@ -ed17b3e95dc3fc3264a4c91843da824f5541f3e1 +51816cd01deee5cc1d7d2c6e1e24788ec655b73e The first line of this file holds the git revision number of the last merge done from the dlang/dmd repository. diff --git a/gcc/d/dmd/expressionsem.d b/gcc/d/dmd/expressionsem.d index b0278cbaca1b..19111e31baa0 100644 --- a/gcc/d/dmd/expressionsem.d +++ b/gcc/d/dmd/expressionsem.d @@ -641,21 +641,25 @@ TupleDeclaration isAliasThisTuple(Expression e) Type t = e.type.toBasetype(); while (true) { -Dsymbol s = t.toDsymbol(null); -if (!s) -return null; -auto ad = s.isAggregateDeclaration(); -if (!ad) -return null; -s = ad.aliasthis ? ad.aliasthis.sym : null; -if (s && s.isVarDeclaration()) +if (Dsymbol s = t.toDsymbol(null)) { -TupleDeclaration td = s.isVarDeclaration().toAlias().isTupleDeclaration(); -if (td && td.isexp) -return td; +if (auto ad = s.isAggregateDeclaration()) +{ +s = ad.aliasthis ? ad.aliasthis.sym : null; +if (s && s.isVarDeclaration()) +{ +TupleDeclaration td = s.isVarDeclaration().toAlias().isTupleDeclaration(); +if (td && td.isexp) +return td; +} +if (Type att = t.aliasthisOf()) +{ +t = att; +continue; +} +} } -if (Type att = t.aliasthisOf()) -t = att; +return null; } } diff --git a/gcc/testsuite/gdc.test/compilable/test21153.d b/gcc/testsuite/gdc.test/compilable/test21153.d new file mode 100644 index ..cd92a31240be --- /dev/null +++ b/gcc/testsuite/gdc.test/compilable/test21153.d @@ -0,0 +1,8 @@ +// https://github.com/dlang/dmd/issues/21153 +alias AliasSeq(TList...) = TList; +class DataClass; +void reduce(DataClass[] r) +{ +alias Args = AliasSeq!(DataClass); +Args result = r[0]; +}
[gcc r15-9294] gccrs: Remove unused error constructor and getter
https://gcc.gnu.org/g:a3148850a5ac0640b0b352a387e6df5c958861a9 commit r15-9294-ga3148850a5ac0640b0b352a387e6df5c958861a9 Author: Pierre-Emmanuel Patry Date: Tue Apr 1 16:08:37 2025 +0200 gccrs: Remove unused error constructor and getter These constructor for eroneous state are not in use anymore since we replaced this error state with an optional in the parent nodes. gcc/rust/ChangeLog: * ast/rust-expr.h: Remove error getter and constructor. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/rust/ast/rust-expr.h | 5 - 1 file changed, 5 deletions(-) diff --git a/gcc/rust/ast/rust-expr.h b/gcc/rust/ast/rust-expr.h index 3ce78c643c73..e6cfa2709f93 100644 --- a/gcc/rust/ast/rust-expr.h +++ b/gcc/rust/ast/rust-expr.h @@ -31,11 +31,6 @@ public: {} // Returns whether the LoopLabel is in an error state. - bool is_error () const { return label.is_error (); } - - // Creates an error state LoopLabel. - static LoopLabel error () { return LoopLabel (Lifetime::error ()); } - location_t get_locus () const { return locus; } Lifetime &get_lifetime () { return label; }
[gcc r15-9301] gccrs: Rename label getter in ContinueExpr
https://gcc.gnu.org/g:c4ec1bc7b2ff98e20b20fd34a490b0d711b19f2c commit r15-9301-gc4ec1bc7b2ff98e20b20fd34a490b0d711b19f2c Author: Pierre-Emmanuel Patry Date: Thu Apr 3 14:40:15 2025 +0200 gccrs: Rename label getter in ContinueExpr gcc/rust/ChangeLog: * ast/rust-ast-collector.cc (TokenCollector::visit): Call unchecked getter. * ast/rust-ast-visitor.cc (DefaultASTVisitor::visit): Likewise. * ast/rust-ast.cc (ContinueExpr::as_string): Likewise. * hir/rust-ast-lower-expr.cc (ASTLoweringExpr::visit): Likewise. * resolve/rust-ast-resolve-expr.cc (ResolveExpr::visit): Likewise. * resolve/rust-late-name-resolver-2.0.cc (Late::visit): Likewise. * ast/rust-expr.h: Add new getter for the optional and rename getter to get_label_unchecked. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/rust/ast/rust-ast-collector.cc | 2 +- gcc/rust/ast/rust-ast-visitor.cc| 2 +- gcc/rust/ast/rust-ast.cc| 2 +- gcc/rust/ast/rust-expr.h| 7 +-- gcc/rust/hir/rust-ast-lower-expr.cc | 2 +- gcc/rust/resolve/rust-ast-resolve-expr.cc | 6 +++--- gcc/rust/resolve/rust-late-name-resolver-2.0.cc | 2 +- 7 files changed, 13 insertions(+), 10 deletions(-) diff --git a/gcc/rust/ast/rust-ast-collector.cc b/gcc/rust/ast/rust-ast-collector.cc index 3297407e6e82..165b7617fe4a 100644 --- a/gcc/rust/ast/rust-ast-collector.cc +++ b/gcc/rust/ast/rust-ast-collector.cc @@ -1279,7 +1279,7 @@ TokenCollector::visit (ContinueExpr &expr) { push (Rust::Token::make (CONTINUE, expr.get_locus ())); if (expr.has_label ()) -visit (expr.get_label ()); +visit (expr.get_label_unchecked ()); } void diff --git a/gcc/rust/ast/rust-ast-visitor.cc b/gcc/rust/ast/rust-ast-visitor.cc index b72e063987f3..702a176b266a 100644 --- a/gcc/rust/ast/rust-ast-visitor.cc +++ b/gcc/rust/ast/rust-ast-visitor.cc @@ -478,7 +478,7 @@ DefaultASTVisitor::visit (AST::ContinueExpr &expr) { visit_outer_attrs (expr); if (expr.has_label ()) -visit (expr.get_label ()); +visit (expr.get_label_unchecked ()); } void diff --git a/gcc/rust/ast/rust-ast.cc b/gcc/rust/ast/rust-ast.cc index 1d92bf3b1636..670e6d2413d1 100644 --- a/gcc/rust/ast/rust-ast.cc +++ b/gcc/rust/ast/rust-ast.cc @@ -1631,7 +1631,7 @@ ContinueExpr::as_string () const std::string str ("continue "); if (has_label ()) -str += get_label ().as_string (); +str += get_label_unchecked ().as_string (); return str; } diff --git a/gcc/rust/ast/rust-expr.h b/gcc/rust/ast/rust-expr.h index 70cb6d403551..4c832f9a06f4 100644 --- a/gcc/rust/ast/rust-expr.h +++ b/gcc/rust/ast/rust-expr.h @@ -2879,8 +2879,11 @@ public: outer_attrs = std::move (new_attrs); } - Lifetime &get_label () { return label.value (); } - const Lifetime &get_label () const { return label.value (); } + Lifetime &get_label_unchecked () { return label.value (); } + const Lifetime &get_label_unchecked () const { return label.value (); } + + tl::optional &get_label () { return label; } + const tl::optional &get_label () const { return label; } Expr::Kind get_expr_kind () const override { return Expr::Kind::Continue; } diff --git a/gcc/rust/hir/rust-ast-lower-expr.cc b/gcc/rust/hir/rust-ast-lower-expr.cc index ea1623f809e6..944c0bbf4d15 100644 --- a/gcc/rust/hir/rust-ast-lower-expr.cc +++ b/gcc/rust/hir/rust-ast-lower-expr.cc @@ -622,7 +622,7 @@ ASTLoweringExpr::visit (AST::ContinueExpr &expr) { tl::optional break_label; if (expr.has_label ()) -break_label = lower_lifetime (expr.get_label ()); +break_label = lower_lifetime (expr.get_label_unchecked ()); auto crate_num = mappings.get_current_crate (); Analysis::NodeMapping mapping (crate_num, expr.get_node_id (), diff --git a/gcc/rust/resolve/rust-ast-resolve-expr.cc b/gcc/rust/resolve/rust-ast-resolve-expr.cc index 4bfd1b3ca4fe..54d92854128c 100644 --- a/gcc/rust/resolve/rust-ast-resolve-expr.cc +++ b/gcc/rust/resolve/rust-ast-resolve-expr.cc @@ -594,7 +594,7 @@ ResolveExpr::visit (AST::ContinueExpr &expr) { if (expr.has_label ()) { - auto label = expr.get_label (); + auto label = expr.get_label_unchecked (); if (label.get_lifetime_type () != AST::Lifetime::LifetimeType::NAMED) { rust_error_at (label.get_locus (), @@ -608,8 +608,8 @@ ResolveExpr::visit (AST::ContinueExpr &expr) label.get_lifetime_name ()), &resolved_node)) { - rust_error_at (expr.get_label ().get_locus (), ErrorCode::E0426, -"use of undeclared label %qs", + rust_error_at (expr.get_label_unchecked ().get_locus (), +ErrorCode::E0426, "use of undeclared label %qs", label.as_string ().c_str ()); return; } diff --
[gcc r14-11540] libstdc++: Replace use of __mindist in ranges::uninitialized_xxx algos [PR101587]
https://gcc.gnu.org/g:7ad64ffe10f87cbd28f0d9719469edda61b8 commit r14-11540-g7ad64ffe10f87cbd28f0d9719469edda61b8 Author: Jonathan Wakely Date: Wed Mar 26 11:47:05 2025 + libstdc++: Replace use of __mindist in ranges::uninitialized_xxx algos [PR101587] In r15-8980-gf4b6acfc36fb1f I introduced a new function object for finding the smaller of two distances. In bugzilla Hewill Kang pointed out that we still need to explicitly convert the result back to the right difference type, because the result might be an integer-like class type that doesn't convert to an integral type explicitly. Rather than doing that conversion in the __mindist function object, I think it's simpler to remove it again and just do a comparison and assignment. We always want the result to have a specific type, so we can just check if the value of the other type is smaller, and then convert that to the other type if so. libstdc++-v3/ChangeLog: PR libstdc++/101587 * include/bits/ranges_uninitialized.h (__detail::__mindist): Remove. (ranges::uninitialized_copy, ranges::uninitialized_copy_n) (ranges::uninitialized_move, ranges::uninitialized_move_n): Use comparison and assignment instead of __mindist. * testsuite/20_util/specialized_algorithms/uninitialized_copy/constrained.cc: Check with ranges that use integer-like class type for difference type. * testsuite/20_util/specialized_algorithms/uninitialized_move/constrained.cc: Likewise. Reviewed-by: Tomasz Kaminski Reviewed-by: Hewill Kang (cherry picked from commit 03ac8886e5c1fa16da90276fd721a57fa9435f4f) Diff: --- libstdc++-v3/include/bits/ranges_uninitialized.h | 46 +++--- .../uninitialized_copy/constrained.cc | 30 +- .../uninitialized_move/constrained.cc | 29 +- 3 files changed, 71 insertions(+), 34 deletions(-) diff --git a/libstdc++-v3/include/bits/ranges_uninitialized.h b/libstdc++-v3/include/bits/ranges_uninitialized.h index 99a11f0fa7cc..3e9851630fa2 100644 --- a/libstdc++-v3/include/bits/ranges_uninitialized.h +++ b/libstdc++-v3/include/bits/ranges_uninitialized.h @@ -252,26 +252,6 @@ namespace ranges inline constexpr __uninitialized_value_construct_n_fn uninitialized_value_construct_n; - namespace __detail - { -// This is only intended for finding smaller iterator differences below, -// not as a general purpose replacement for std::min. -struct __mindist_fn -{ - template - constexpr common_type_t<_Dp1, _Dp2> - operator()(_Dp1 __d1, _Dp2 __d2) const noexcept - { - // Every C++20 iterator I satisfies weakly_incrementable which - // requires signed-integer-like>. - static_assert(std::__detail::__is_signed_integer_like<_Dp1>); - static_assert(std::__detail::__is_signed_integer_like<_Dp2>); - return std::min>(__d1, __d2); - } -}; -inline constexpr __mindist_fn __mindist{}; - } - template using uninitialized_copy_result = in_out_result<_Iter, _Out>; @@ -292,10 +272,10 @@ namespace ranges && is_nothrow_assignable_v<_OutType&, iter_reference_t<_Iter>>) { - auto __d1 = __ilast - __ifirst; - auto __d2 = __olast - __ofirst; - return ranges::copy_n(std::move(__ifirst), - __detail::__mindist(__d1, __d2), __ofirst); + auto __d = __ilast - __ifirst; + if (auto __d2 = __olast - __ofirst; __d2 < __d) + __d = static_cast>(__d2); + return ranges::copy_n(std::move(__ifirst), __d, __ofirst); } else { @@ -340,9 +320,9 @@ namespace ranges && is_nothrow_assignable_v<_OutType&, iter_reference_t<_Iter>>) { - auto __d = __olast - __ofirst; - return ranges::copy_n(std::move(__ifirst), - __detail::__mindist(__n, __d), __ofirst); + if (auto __d = __olast - __ofirst; __d < __n) + __n = static_cast>(__d); + return ranges::copy_n(std::move(__ifirst), __n, __ofirst); } else { @@ -379,11 +359,12 @@ namespace ranges && is_nothrow_assignable_v<_OutType&, iter_rvalue_reference_t<_Iter>>) { - auto __d1 = __ilast - __ifirst; - auto __d2 = __olast - __ofirst; + auto __d = __ilast - __ifirst; + if (auto __d2 = __olast - __ofirst; __d2 < __d) + __d = static_cast>(__d2); auto [__in, __out] = ranges::copy_n(std::make_move_iterator(std::move(__ifirst)
[gcc r14-11542] libstdc++: Fix use-after-free in std::format [PR119671]
https://gcc.gnu.org/g:059107eb22c4800be94abb1ff9085341cc851432 commit r14-11542-g059107eb22c4800be94abb1ff9085341cc851432 Author: Jonathan Wakely Date: Mon Apr 7 19:52:55 2025 +0100 libstdc++: Fix use-after-free in std::format [PR119671] When formatting floating-point values to wide strings there's a case where we invalidate a std::wstring buffer while a std::wstring_view is still referring to it. libstdc++-v3/ChangeLog: PR libstdc++/119671 * include/std/format (__formatter_fp::format): Do not invalidate __wstr unless _M_localized returns a valid string. * testsuite/std/format/functions/format.cc: Check wide string formatting of floating-point types with classic locale. Reviewed-by: Tomasz Kaminski (cherry picked from commit e33b62eed7fd0a82d758b23252d288585b6790d2) Diff: --- libstdc++-v3/include/std/format | 6 +++--- libstdc++-v3/testsuite/std/format/functions/format.cc | 12 2 files changed, 15 insertions(+), 3 deletions(-) diff --git a/libstdc++-v3/include/std/format b/libstdc++-v3/include/std/format index 15bded87c9cd..b8830766f40f 100644 --- a/libstdc++-v3/include/std/format +++ b/libstdc++-v3/include/std/format @@ -1751,9 +1751,9 @@ namespace __format if (_M_spec._M_localized && __builtin_isfinite(__v)) { - __wstr = _M_localize(__str, __expc, __fc.locale()); - if (!__wstr.empty()) - __str = __wstr; + auto __s = _M_localize(__str, __expc, __fc.locale()); + if (!__s.empty()) + __str = __wstr = std::move(__s); } size_t __width = _M_spec._M_get_width(__fc); diff --git a/libstdc++-v3/testsuite/std/format/functions/format.cc b/libstdc++-v3/testsuite/std/format/functions/format.cc index 78010e159d36..d6575dabb6bc 100644 --- a/libstdc++-v3/testsuite/std/format/functions/format.cc +++ b/libstdc++-v3/testsuite/std/format/functions/format.cc @@ -366,6 +366,18 @@ test_wchar() // P2909R4 Fix formatting of code units as integers (Dude, where’s my char?) s = std::format(L"{:d} {:d}", wchar_t(-1), char(-1)); VERIFY( s.find('-') == std::wstring::npos ); + + auto ws = std::format(L"{:L}", 0.5); + VERIFY( ws == L"0.5" ); + // The default C locale. + std::locale cloc = std::locale::classic(); + // PR libstdc++/119671 use-after-free formatting floating-point to wstring + ws = std::format(cloc, L"{:L}", 0.5); + VERIFY( ws == L"0.5" ); + // A locale with no name, but with the same facets as the C locale. + std::locale locx(cloc, &std::use_facet>(cloc)); + ws = std::format(locx, L"{:L}", 0.5); + VERIFY( ws == L"0.5" ); } void
[gcc r14-11541] libstdc++: Add new header to Doxygen config file
https://gcc.gnu.org/g:7e789f34206f29ae501ddba87faf0e73658a4c5c commit r14-11541-g7e789f34206f29ae501ddba87faf0e73658a4c5c Author: Jonathan Wakely Date: Thu Apr 3 15:36:08 2025 +0100 libstdc++: Add new header to Doxygen config file libstdc++-v3/ChangeLog: * doc/doxygen/user.cfg.in (INPUT): Add text_encoding. (cherry picked from commit 5430fcd1a3222d62c1b9560de251268c8bc50303) Diff: --- libstdc++-v3/doc/doxygen/user.cfg.in | 1 + 1 file changed, 1 insertion(+) diff --git a/libstdc++-v3/doc/doxygen/user.cfg.in b/libstdc++-v3/doc/doxygen/user.cfg.in index 8fe337adf751..5672c207accd 100644 --- a/libstdc++-v3/doc/doxygen/user.cfg.in +++ b/libstdc++-v3/doc/doxygen/user.cfg.in @@ -906,6 +906,7 @@ INPUT = @srcdir@/doc/doxygen/doxygroups.cc \ include/string_view \ include/syncstream \ include/system_error \ + include/text_encoding \ include/thread \ include/tuple \ include/typeindex \
[gcc r15-9299] gccrs: Adapt testcase to name resolution 2.0
https://gcc.gnu.org/g:7ae95869c83ae3ff23c97292a43bedbfe3387364 commit r15-9299-g7ae95869c83ae3ff23c97292a43bedbfe3387364 Author: Pierre-Emmanuel Patry Date: Wed Apr 2 18:20:54 2025 +0200 gccrs: Adapt testcase to name resolution 2.0 Name resolution 2.0 behavior matches more closely rustc's behavior and trying to prevent undeclared label error emission would break some other test. gcc/testsuite/ChangeLog: * rust/compile/invalid_label_name.rs: Adapt test to nr2. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/testsuite/rust/compile/invalid_label_name.rs | 4 1 file changed, 4 insertions(+) diff --git a/gcc/testsuite/rust/compile/invalid_label_name.rs b/gcc/testsuite/rust/compile/invalid_label_name.rs index 5c850da636cb..66e40a620e09 100644 --- a/gcc/testsuite/rust/compile/invalid_label_name.rs +++ b/gcc/testsuite/rust/compile/invalid_label_name.rs @@ -1,20 +1,24 @@ +// { dg-additional-options "-frust-name-resolution-2.0" } pub fn function() { 'continue: loop { // { dg-error "invalid label name .'continue." "" { target *-*-* } .-1 } break 'extern; // { dg-error "invalid label name .'extern." "" { target *-*-* } .-1 } +// { dg-error "use of undeclared label .'extern." "" { target *-*-* } .-2 } } 'break: loop { // { dg-error "invalid label name .'break." "" { target *-*-* } .-1 } break 'for; // { dg-error "invalid label name .'for." "" { target *-*-* } .-1 } +// { dg-error "use of undeclared label .'for." "" { target *-*-* } .-2 } } 'crate: loop { // { dg-error "invalid label name .'crate." "" { target *-*-* } .-1 } break 'loop; // { dg-error "invalid label name .'loop." "" { target *-*-* } .-1 } +// { dg-error "use of undeclared label .'loop." "" { target *-*-* } .-2 } } 'a: loop {
[gcc/devel/rust/master] hir: Add default qualifier to function, lower it properly
https://gcc.gnu.org/g:861dcf6f8f7b2e50f8dcbe59338cac8cac8efd26 commit 861dcf6f8f7b2e50f8dcbe59338cac8cac8efd26 Author: Arthur Cohen Date: Tue Apr 1 17:45:28 2025 +0200 hir: Add default qualifier to function, lower it properly gcc/rust/ChangeLog: * ast/rust-ast.cc (Function::Function): Rename is_default -> has_default. (Function::operator=): Likewise. * ast/rust-item.h (class Function): Add `is_default` method. * hir/rust-ast-lower-implitem.cc (ASTLowerImplItem::visit): Lower default qualifier. * hir/rust-ast-lower-item.cc (ASTLoweringItem::visit): Likewise. * hir/tree/rust-hir-item.cc (Function::Function): Add `is_default` member. (Function::operator=): Likewise. * hir/tree/rust-hir-item.h (enum class Defaultness): New enum. (class Function): Use it. gcc/testsuite/ChangeLog: * rust/compile/min_specialization1.rs: New test. Diff: --- gcc/rust/ast/rust-ast.cc | 4 ++-- gcc/rust/ast/rust-item.h | 8 +--- gcc/rust/hir/rust-ast-lower-implitem.cc | 6 +- gcc/rust/hir/rust-ast-lower-item.cc | 5 - gcc/rust/hir/tree/rust-hir-item.cc| 9 ++--- gcc/rust/hir/tree/rust-hir-item.h | 17 - gcc/testsuite/rust/compile/min_specialization1.rs | 15 +++ 7 files changed, 53 insertions(+), 11 deletions(-) diff --git a/gcc/rust/ast/rust-ast.cc b/gcc/rust/ast/rust-ast.cc index 02641043f94a..43f1ee2f5266 100644 --- a/gcc/rust/ast/rust-ast.cc +++ b/gcc/rust/ast/rust-ast.cc @@ -1068,7 +1068,7 @@ Function::Function (Function const &other) : VisItem (other), ExternalItem (other.get_node_id ()), qualifiers (other.qualifiers), function_name (other.function_name), where_clause (other.where_clause), locus (other.locus), -is_default (other.is_default), +has_default (other.has_default), is_external_function (other.is_external_function) { // guard to prevent null dereference (always required) @@ -1100,7 +1100,7 @@ Function::operator= (Function const &other) // visibility = other.visibility->clone_visibility(); // outer_attrs = other.outer_attrs; locus = other.locus; - is_default = other.is_default; + has_default = other.has_default; is_external_function = other.is_external_function; // guard to prevent null dereference (always required) diff --git a/gcc/rust/ast/rust-item.h b/gcc/rust/ast/rust-item.h index 189382239a25..0c94f168f869 100644 --- a/gcc/rust/ast/rust-item.h +++ b/gcc/rust/ast/rust-item.h @@ -1330,7 +1330,7 @@ class Function : public VisItem, public AssociatedItem, public ExternalItem WhereClause where_clause; tl::optional> function_body; location_t locus; - bool is_default; + bool has_default; bool is_external_function; public: @@ -1355,6 +1355,8 @@ public: bool has_body () const { return function_body.has_value (); } + bool is_default () const { return has_default; } + // Mega-constructor with all possible fields Function (Identifier function_name, FunctionQualifiers qualifiers, std::vector> generic_params, @@ -1362,7 +1364,7 @@ public: std::unique_ptr return_type, WhereClause where_clause, tl::optional> function_body, Visibility vis, std::vector outer_attrs, - location_t locus, bool is_default = false, + location_t locus, bool has_default = false, bool is_external_function = false) : VisItem (std::move (vis), std::move (outer_attrs)), ExternalItem (Stmt::node_id), qualifiers (std::move (qualifiers)), @@ -1372,7 +1374,7 @@ public: return_type (std::move (return_type)), where_clause (std::move (where_clause)), function_body (std::move (function_body)), locus (locus), - is_default (is_default), is_external_function (is_external_function) + has_default (has_default), is_external_function (is_external_function) {} // TODO: add constructor with less fields diff --git a/gcc/rust/hir/rust-ast-lower-implitem.cc b/gcc/rust/hir/rust-ast-lower-implitem.cc index 7b64f7edebe8..3229f57c38f2 100644 --- a/gcc/rust/hir/rust-ast-lower-implitem.cc +++ b/gcc/rust/hir/rust-ast-lower-implitem.cc @@ -22,6 +22,7 @@ #include "rust-ast-lower-expr.h" #include "rust-ast-lower-pattern.h" #include "rust-ast-lower-block.h" +#include "rust-hir-item.h" #include "rust-item.h" namespace Rust { @@ -140,6 +141,9 @@ ASTLowerImplItem::visit (AST::Function &function) ASTLoweringType::translate (function.get_return_type ())) : nullptr; + Defaultness defaultness += function.is_default () ? Defaultness::Default : Defaultness::Final; + std::vector function_params; for (auto &p : function.get_function_params ()) { @@ -183,7 +187,7 @@ ASTLowerImplItem::visit (AST::Function &function)
[gcc/devel/rust/master] Adapt testcase to name resolution 2.0
https://gcc.gnu.org/g:a179c05f228cace7bcaba8c550e0550993ff5a46 commit a179c05f228cace7bcaba8c550e0550993ff5a46 Author: Pierre-Emmanuel Patry Date: Wed Apr 2 18:20:54 2025 +0200 Adapt testcase to name resolution 2.0 Name resolution 2.0 behavior matches more closely rustc's behavior and trying to prevent undeclared label error emission would break some other test. gcc/testsuite/ChangeLog: * rust/compile/invalid_label_name.rs: Adapt test to nr2. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/testsuite/rust/compile/invalid_label_name.rs | 4 1 file changed, 4 insertions(+) diff --git a/gcc/testsuite/rust/compile/invalid_label_name.rs b/gcc/testsuite/rust/compile/invalid_label_name.rs index 5c850da636cb..66e40a620e09 100644 --- a/gcc/testsuite/rust/compile/invalid_label_name.rs +++ b/gcc/testsuite/rust/compile/invalid_label_name.rs @@ -1,20 +1,24 @@ +// { dg-additional-options "-frust-name-resolution-2.0" } pub fn function() { 'continue: loop { // { dg-error "invalid label name .'continue." "" { target *-*-* } .-1 } break 'extern; // { dg-error "invalid label name .'extern." "" { target *-*-* } .-1 } +// { dg-error "use of undeclared label .'extern." "" { target *-*-* } .-2 } } 'break: loop { // { dg-error "invalid label name .'break." "" { target *-*-* } .-1 } break 'for; // { dg-error "invalid label name .'for." "" { target *-*-* } .-1 } +// { dg-error "use of undeclared label .'for." "" { target *-*-* } .-2 } } 'crate: loop { // { dg-error "invalid label name .'crate." "" { target *-*-* } .-1 } break 'loop; // { dg-error "invalid label name .'loop." "" { target *-*-* } .-1 } +// { dg-error "use of undeclared label .'loop." "" { target *-*-* } .-2 } } 'a: loop {
[gcc/devel/rust/master] Resolve labels
https://gcc.gnu.org/g:be0d14806500f75266d2ad507cf7018de6a24766 commit be0d14806500f75266d2ad507cf7018de6a24766 Author: Pierre-Emmanuel Patry Date: Mon Mar 31 17:00:11 2025 +0200 Resolve labels gcc/rust/ChangeLog: * hir/rust-ast-lower.cc (ASTLoweringBlock::visit): Lower label only if it exists. * hir/tree/rust-hir-expr.cc (BlockExpr::BlockExpr): Make loop label optional. (BaseLoopExpr::BaseLoopExpr): Likewise. (LoopExpr::LoopExpr): Likewise. (WhileLoopExpr::WhileLoopExpr): Likewise. * hir/tree/rust-hir-expr.h: Use optional for lifetime and labels. * hir/tree/rust-hir.cc (WhileLoopExpr::as_string): Use getter. (WhileLetLoopExpr::as_string): Likewise. (LoopExpr::as_string): Likewise. * resolve/rust-late-name-resolver-2.0.cc (Late::visit): Resolve labels. * resolve/rust-late-name-resolver-2.0.h: Add visit function prototype for loop labels. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/rust/hir/rust-ast-lower.cc | 6 +- gcc/rust/hir/tree/rust-hir-expr.cc | 14 +- gcc/rust/hir/tree/rust-hir-expr.h | 25 ++--- gcc/rust/hir/tree/rust-hir.cc | 6 +++--- gcc/rust/resolve/rust-late-name-resolver-2.0.cc | 19 +++ gcc/rust/resolve/rust-late-name-resolver-2.0.h | 1 + 6 files changed, 51 insertions(+), 20 deletions(-) diff --git a/gcc/rust/hir/rust-ast-lower.cc b/gcc/rust/hir/rust-ast-lower.cc index b778fb5dbee4..c6446aa1bcbd 100644 --- a/gcc/rust/hir/rust-ast-lower.cc +++ b/gcc/rust/hir/rust-ast-lower.cc @@ -97,7 +97,11 @@ ASTLowering::go () void ASTLoweringBlock::visit (AST::BlockExpr &expr) { - auto label = lower_loop_label (expr.get_label ()); + tl::optional label; + if (expr.has_label ()) +label = lower_loop_label (expr.get_label ()); + else +label = tl::nullopt; std::vector> block_stmts; bool block_did_terminate = false; diff --git a/gcc/rust/hir/tree/rust-hir-expr.cc b/gcc/rust/hir/tree/rust-hir-expr.cc index bb7ebfbc617b..82a09e935887 100644 --- a/gcc/rust/hir/tree/rust-hir-expr.cc +++ b/gcc/rust/hir/tree/rust-hir-expr.cc @@ -749,7 +749,7 @@ BlockExpr::BlockExpr (Analysis::NodeMapping mappings, std::vector> block_statements, std::unique_ptr block_expr, bool tail_reachable, AST::AttrVec inner_attribs, AST::AttrVec outer_attribs, - LoopLabel label, location_t start_locus, + tl::optional label, location_t start_locus, location_t end_locus) : ExprWithBlock (std::move (mappings), std::move (outer_attribs)), WithInnerAttrs (std::move (inner_attribs)), @@ -985,7 +985,8 @@ UnsafeBlockExpr::operator= (UnsafeBlockExpr const &other) BaseLoopExpr::BaseLoopExpr (Analysis::NodeMapping mappings, std::unique_ptr loop_block, - location_t locus, LoopLabel loop_label, + location_t locus, + tl::optional loop_label, AST::AttrVec outer_attribs) : ExprWithBlock (std::move (mappings), std::move (outer_attribs)), loop_label (std::move (loop_label)), loop_block (std::move (loop_block)), @@ -1011,7 +1012,8 @@ BaseLoopExpr::operator= (BaseLoopExpr const &other) LoopExpr::LoopExpr (Analysis::NodeMapping mappings, std::unique_ptr loop_block, location_t locus, - LoopLabel loop_label, AST::AttrVec outer_attribs) + tl::optional loop_label, + AST::AttrVec outer_attribs) : BaseLoopExpr (std::move (mappings), std::move (loop_block), locus, std::move (loop_label), std::move (outer_attribs)) {} @@ -1019,7 +1021,8 @@ LoopExpr::LoopExpr (Analysis::NodeMapping mappings, WhileLoopExpr::WhileLoopExpr (Analysis::NodeMapping mappings, std::unique_ptr loop_condition, std::unique_ptr loop_block, - location_t locus, LoopLabel loop_label, + location_t locus, + tl::optional loop_label, AST::AttrVec outer_attribs) : BaseLoopExpr (std::move (mappings), std::move (loop_block), locus, std::move (loop_label), std::move (outer_attribs)), @@ -1046,7 +1049,8 @@ WhileLetLoopExpr::WhileLetLoopExpr ( Analysis::NodeMapping mappings, std::vector> match_arm_patterns, std::unique_ptr condition, std::unique_ptr loop_block, - location_t locus, LoopLabel loop_label, AST::AttrVec outer_attribs) + location_t locus, tl::optional loop_label, + AST::AttrVec outer_attribs) : BaseLoopExpr (std::move (mappings), std::move (loop_block), locus,
[gcc/devel/rust/master] Fix unresolved label error message
https://gcc.gnu.org/g:5562e72c96ef45a561c7ec0e9bf6f1ebb87b982c commit 5562e72c96ef45a561c7ec0e9bf6f1ebb87b982c Author: Pierre-Emmanuel Patry Date: Wed Apr 2 17:38:28 2025 +0200 Fix unresolved label error message gcc/rust/ChangeLog: * resolve/rust-ast-resolve-expr.cc (ResolveExpr::visit): Change error message to match rustc. gcc/testsuite/ChangeLog: * rust/compile/undeclared_label.rs: Change test expected string. Signed-off-by: Pierre-Emmanuel Patry Diff: --- gcc/rust/resolve/rust-ast-resolve-expr.cc | 8 gcc/testsuite/rust/compile/undeclared_label.rs | 4 ++-- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/gcc/rust/resolve/rust-ast-resolve-expr.cc b/gcc/rust/resolve/rust-ast-resolve-expr.cc index 1e10e3b0692c..d83663810262 100644 --- a/gcc/rust/resolve/rust-ast-resolve-expr.cc +++ b/gcc/rust/resolve/rust-ast-resolve-expr.cc @@ -486,8 +486,8 @@ ResolveExpr::visit (AST::BreakExpr &expr) &resolved_node)) { rust_error_at (label.get_locus (), ErrorCode::E0426, -"use of undeclared label %qs in %", -label.get_lifetime_name ().c_str ()); +"use of undeclared label %qs", +label.as_string ().c_str ()); return; } resolver->insert_resolved_label (label.get_node_id (), resolved_node); @@ -609,8 +609,8 @@ ResolveExpr::visit (AST::ContinueExpr &expr) &resolved_node)) { rust_error_at (expr.get_label ().get_locus (), ErrorCode::E0426, -"use of undeclared label %qs in %", -label.get_lifetime_name ().c_str ()); +"use of undeclared label %qs", +label.as_string ().c_str ()); return; } resolver->insert_resolved_label (label.get_node_id (), resolved_node); diff --git a/gcc/testsuite/rust/compile/undeclared_label.rs b/gcc/testsuite/rust/compile/undeclared_label.rs index 6efa2d98dbfb..9aa0553f6572 100644 --- a/gcc/testsuite/rust/compile/undeclared_label.rs +++ b/gcc/testsuite/rust/compile/undeclared_label.rs @@ -2,12 +2,12 @@ #![allow(unused)] fn resolve_label_continue() -> () { loop { -continue 'a; // { dg-error "use of undeclared label .a. in .continue." } +continue 'a; // { dg-error "use of undeclared label .'a." } } } fn resolve_label_break() -> () { loop { -break 'crabby; // { dg-error "use of undeclared label .crabby. in .break." } +break 'crabby; // { dg-error "use of undeclared label .'crabby." } } } fn main() {
[gcc r15-9322] testsuite: Update guality XFAILs for aarch64
https://gcc.gnu.org/g:ed14cb27b6c8c46bed55ae7ff4ad837c33e2c6e0 commit r15-9322-ged14cb27b6c8c46bed55ae7ff4ad837c33e2c6e0 Author: Richard Sandiford Date: Tue Apr 8 22:03:39 2025 +0100 testsuite: Update guality XFAILs for aarch64 In previous years, I've tried to update the guality tests so that they give clean results on aarch64-linux-gnu with a recent version of GDB. This patch does the same thing for GCC 15. The version of GDB I used was 16.2. As before, there are no PRs for the XFAILs. The idea is that anyone who is interested in working in this area can see the current XFAILs by grepping the tests. gcc/testsuite/ * gcc.dg/guality/pr36728-3.c: Update XFAILs for aarch64. * gcc.dg/guality/pr41353-1.c: Likewise. * gcc.dg/guality/pr54693-2.c: Likewise. * gcc.dg/guality/pr68860-1.c: Likewise. * gcc.dg/guality/pr68860-2.c: Likewise. * gcc.dg/guality/sra-1.c: Likewise. * gcc.dg/guality/vla-1.c: Likewise. Diff: --- gcc/testsuite/gcc.dg/guality/pr36728-3.c | 2 +- gcc/testsuite/gcc.dg/guality/pr41353-1.c | 2 +- gcc/testsuite/gcc.dg/guality/pr54693-2.c | 2 +- gcc/testsuite/gcc.dg/guality/pr68860-1.c | 2 +- gcc/testsuite/gcc.dg/guality/pr68860-2.c | 2 +- gcc/testsuite/gcc.dg/guality/sra-1.c | 2 +- gcc/testsuite/gcc.dg/guality/vla-1.c | 4 ++-- 7 files changed, 8 insertions(+), 8 deletions(-) diff --git a/gcc/testsuite/gcc.dg/guality/pr36728-3.c b/gcc/testsuite/gcc.dg/guality/pr36728-3.c index 4700d50f8bcd..589009b2e82c 100644 --- a/gcc/testsuite/gcc.dg/guality/pr36728-3.c +++ b/gcc/testsuite/gcc.dg/guality/pr36728-3.c @@ -30,7 +30,7 @@ foo (int arg1, int arg2, int arg3, int arg4, int arg5, int arg6, int arg7) /* { dg-final { gdb-test 14 "arg5" "5" } } */ /* { dg-final { gdb-test 14 "arg6" "6" } } */ /* { dg-final { gdb-test 14 "arg7" "30" } } */ -/* { dg-final { gdb-test 14 "y" "2" } } */ +/* { dg-final { gdb-test 14 "y" "2" { xfail { aarch64*-*-* && { any-opts "-O3" } } } } } */ /* { dg-final { gdb-test 16 "arg1" "1" { target { ! "s390*-*-*" } } } } */ /* { dg-final { gdb-test 16 "arg2" "2" { target { ! "s390*-*-*" } } } } */ /* { dg-final { gdb-test 16 "arg3" "3" } } */ diff --git a/gcc/testsuite/gcc.dg/guality/pr41353-1.c b/gcc/testsuite/gcc.dg/guality/pr41353-1.c index 6639a524f0f2..ead9d892bb59 100644 --- a/gcc/testsuite/gcc.dg/guality/pr41353-1.c +++ b/gcc/testsuite/gcc.dg/guality/pr41353-1.c @@ -22,7 +22,7 @@ f2 (int i, int j) { j += i; /* { dg-final { gdb-test .+4 "i" "37" } } */ - /* { dg-final { gdb-test .+3 "j" "28 + 37" { xfail { no-opts "-O0" } } } } */ + /* { dg-final { gdb-test .+3 "j" "28 + 37" { xfail { { ! aarch64-*-* } && { no-opts "-O0" } } } } } */ int i1 = 2 * i; /* { dg-final { gdb-test .+2 "i1" "2 * 37" } } */ int i2 = 3 * i; /* { dg-final { gdb-test .+1 "i2" "3 * 37" } } */ return j; diff --git a/gcc/testsuite/gcc.dg/guality/pr54693-2.c b/gcc/testsuite/gcc.dg/guality/pr54693-2.c index 7a0ae73c3eeb..229ef0efbea0 100644 --- a/gcc/testsuite/gcc.dg/guality/pr54693-2.c +++ b/gcc/testsuite/gcc.dg/guality/pr54693-2.c @@ -18,7 +18,7 @@ foo (int x, int y, int z) while (x > 3 && y > 3 && z > 3) { /* { dg-final { gdb-test .+2 "i" "v + 1" } } */ /* { dg-final { gdb-test .+1 "x" "10 - i" { xfail { aarch64*-*-* && { any-opts "-fno-fat-lto-objects" } } } } } */ - bar (i); /* { dg-final { gdb-test . "y" "20 - 2 * i" { xfail { aarch64*-*-* && { any-opts "-fno-fat-lto-objects" } } } } } */ + bar (i); /* { dg-final { gdb-test . "y" "20 - 2 * i" { xfail { aarch64*-*-* && { any-opts "-fno-fat-lto-objects" "-Os" } } } } } */ /* { dg-final { gdb-test .-1 "z" "30 - 3 * i" { xfail { aarch64*-*-* && { any-opts "-fno-fat-lto-objects" "-Os" } } } } } */ i++, x--, y -= 2, z -= 3; } diff --git a/gcc/testsuite/gcc.dg/guality/pr68860-1.c b/gcc/testsuite/gcc.dg/guality/pr68860-1.c index 8c8d8354587f..96d3b4341abd 100644 --- a/gcc/testsuite/gcc.dg/guality/pr68860-1.c +++ b/gcc/testsuite/gcc.dg/guality/pr68860-1.c @@ -31,7 +31,7 @@ foo (int arg1, int arg2, int arg3, int arg4, int arg5, int arg6, int arg7, int a /* { dg-final { gdb-test 14 "arg6" "6" } } */ /* { dg-final { gdb-test 14 "arg7" "30" } } */ /* { dg-final { gdb-test 14 "arg8" "7" } } */ -/* { dg-final { gdb-test 14 "y" "2" } } */ +/* { dg-final { gdb-test 14 "y" "2" { xfail { aarch64*-*-* && { any-opts "-O3" } } } } } */ /* { dg-final { gdb-test 16 "arg1" "1" { target { ! "s390*-*-*" } } } } */ /* { dg-final { gdb-test 16 "arg2" "2" { target { ! "s390*-*-*" } } } } */ /* { dg-final { gdb-test 16 "arg3" "3" } } */ diff --git a/gcc/testsuite/gcc.dg/guality/pr68860-2.c b/gcc/testsuite/gcc.dg/guality/pr68860-2.c index 070efbcd10ce..a18a04e60b29 100644 --- a/gcc/testsuite/gcc.dg/guality/pr68860-2.c +++ b/gcc/testsuite/gcc.dg/guality/pr68860-2.c @@ -31,7 +31,7 @@ foo (int arg1, int arg2, int arg3, int
[gcc r14-11545] LoongArch: Fix awk / sed usage for compatibility
https://gcc.gnu.org/g:4d5fd1176d1a5d387dbc53f00324f86a1afa2ecb commit r14-11545-g4d5fd1176d1a5d387dbc53f00324f86a1afa2ecb Author: Yang Yujie Date: Mon Apr 7 10:31:46 2025 +0800 LoongArch: Fix awk / sed usage for compatibility Tested with nawk, mawk, and gawk. gcc/ChangeLog: * config/loongarch/genopts/gen-evolution.awk: remove usage of "asort". * config/loongarch/genopts/genstr.sh: replace sed with awk. (cherry picked from commit 6ed8c17c2bce631ae370d93164ceb6c1b5adf925) Diff: --- gcc/config/loongarch/genopts/gen-evolution.awk | 12 +- gcc/config/loongarch/genopts/genstr.sh | 57 ++ 2 files changed, 40 insertions(+), 29 deletions(-) diff --git a/gcc/config/loongarch/genopts/gen-evolution.awk b/gcc/config/loongarch/genopts/gen-evolution.awk index a2ecd9a8bcf5..97f7b0a33c29 100644 --- a/gcc/config/loongarch/genopts/gen-evolution.awk +++ b/gcc/config/loongarch/genopts/gen-evolution.awk @@ -101,10 +101,18 @@ function gen_cpucfg_useful_idx() idx_list[j++] = i+0 delete idx_bucket -asort (idx_list) +for (i = 1; i < j; i++) { +t = i +for (k = i + 1; k < j; k++) +t = idx_list[k] < idx_list[t] ? k : t + +k = idx_list[t] +idx_list[t] = idx_list[i] +idx_list[i] = k +} print "static constexpr int cpucfg_useful_idx[] = {" -for (i in idx_list) +for (i = 1; i < j; i++) printf(" %d,\n", idx_list[i]) print "};" diff --git a/gcc/config/loongarch/genopts/genstr.sh b/gcc/config/loongarch/genopts/genstr.sh index 5b3bf7fdf0c0..501546d19bc9 100755 --- a/gcc/config/loongarch/genopts/genstr.sh +++ b/gcc/config/loongarch/genopts/genstr.sh @@ -51,18 +51,18 @@ along with GCC; see the file COPYING3. If not see #define LOONGARCH_STR_H EOF -sed -e '/^$/n' -e 's@#.*$@@' -e '/^$/d' \ - -e 's@^\([^ \t]\+\)[ \t]*\([^ \t]*\)@#define \1 "\2"@' \ - loongarch-strings +awk '/^#.*$/ { next } /^$/ { print; next } + { printf ("#define %s \"%s\"\n", $1, $2) }' \ + loongarch-strings echo - # Generate the strings from isa-evolution.in. - awk '{ - a=$3 - gsub(/-/, "_", a) - print("#define OPTSTR_"toupper(a)"\t\""$3"\"") - }' isa-evolution.in +# Generate the strings from isa-evolution.in. +awk '{ + a=$3 + gsub(/-/, "_", a) + print("#define OPTSTR_"toupper(a)"\t\""$3"\"") +}' isa-evolution.in echo echo "#endif /* LOONGARCH_STR_H */" @@ -73,18 +73,8 @@ EOF # according to the key-value pairs defined in loongarch-strings. gen_options() { - -sed -e '/^$/n' -e 's@#.*$@@' -e '/^$/d' \ - -e 's@^\([^ \t]\+\)[ \t]*\([^ \t]*\)@\1="\2"@' \ - loongarch-strings | { \ - - # read the definitions - while read -r line; do - eval "$line" - done - - # print a header - cat << EOF +# print a header +cat << EOF ; Generated by "genstr" from the template "loongarch.opt.in" ; and definitions from "loongarch-strings" and "isa-evolution.in". ; @@ -95,12 +85,25 @@ gen_options() { ; EOF - # make the substitutions - sed -e 's@"@\\"@g' -e 's/@@\([^@]\+\)@@/${\1}/g' loongarch.opt.in | \ - while read -r line; do - eval "echo \"$line\"" - done -} +# Generate loongarch.opt. +awk 'BEGIN { +delete strtab +while (getline < "loongarch-strings" > 0) { +if ($0 ~ /^#.*$/ || $0 ~ /^$/) continue +strtab[$1] = $2 +} +} +{ +n = split($0, tmp, "@@") +for (i = 2; i <= n; i += 2) +tmp[i] = strtab[tmp[i]] + +for (i = 1; i <= n; i++) +printf("%s", tmp[i]) +printf ("\n") + +}' loongarch.opt.in + # Generate the strings from isa-evolution.in. awk '{
[gcc r15-9320] Doc: Copy-edit text about -Wno-xxx [PR90468]
https://gcc.gnu.org/g:5c06ad9ab4a922c86265b2a1b167597c87b646f7 commit r15-9320-g5c06ad9ab4a922c86265b2a1b167597c87b646f7 Author: Sandra Loosemore Date: Tue Apr 8 16:58:05 2025 + Doc: Copy-edit text about -Wno-xxx [PR90468] The issue is specifically about a missing word, but I spotted other copy-editing issues like misplaced hyphens in nearby text. I also thought that the -Wimplicit example was anachronistic because it's a hard error in modern C dialects rather than a warning, and replaced it with something users are more likely to run into. gcc/ChangeLog PR c++/90468 * doc/invoke.texi (Warning Options): Clean up text describing -Wno-xxx. Diff: --- gcc/doc/invoke.texi | 25 + 1 file changed, 13 insertions(+), 12 deletions(-) diff --git a/gcc/doc/invoke.texi b/gcc/doc/invoke.texi index c1d06da4f5bc..a040d65af0e2 100644 --- a/gcc/doc/invoke.texi +++ b/gcc/doc/invoke.texi @@ -6180,10 +6180,11 @@ messages. @end table You can request many specific warnings with options beginning with -@samp{-W}, for example @option{-Wimplicit} to request warnings on -implicit declarations. Each of these specific warning options also -has a negative form beginning @samp{-Wno-} to turn off warnings; for -example, @option{-Wno-implicit}. This manual lists only one of the +@samp{-W}, for example @option{-Wunused-variable} to request warnings on +declarations of variables that are never used. +Each of these specific warning options also +has a negative form beginning with @samp{-Wno-} to turn off warnings; for +example, @option{-Wno-unused-variable}. This manual lists only one of the two forms, whichever is not the default. For further language-specific options also refer to @ref{C++ Dialect Options} and @ref{Objective-C and Objective-C++ Dialect Options}. @@ -6192,15 +6193,15 @@ Additional warnings can be produced by enabling the static analyzer; Some options, such as @option{-Wall} and @option{-Wextra}, turn on other options, such as @option{-Wunused}, which may turn on further options, -such as @option{-Wunused-value}. The combined effect of positive and +such as @option{-Wunused-variable}. The combined effect of positive and negative forms is that more specific options have priority over less -specific ones, independently of their position in the command-line. For +specific ones, independently of their position in the command line. For options of the same specificity, the last one takes effect. Options enabled or disabled via pragmas (@pxref{Diagnostic Pragmas}) take effect -as if they appeared at the end of the command-line. +as if they appeared at the end of the command line. When an unrecognized warning option is requested (e.g., -@option{-Wunknown-warning}), GCC emits a diagnostic stating +@option{-Wunknown-warning}), GCC gives an error stating that the option is not recognized. However, if the @option{-Wno-} form is used, the behavior is slightly different: no diagnostic is produced for @option{-Wno-unknown-warning} unless other diagnostics @@ -6209,11 +6210,11 @@ with old compilers, but if something goes wrong, the compiler warns that an unrecognized option is present. The effectiveness of some warnings depends on optimizations also being -enabled. For example @option{-Wsuggest-final-types} is more effective -with link-time optimization and some instances of other warnings may +enabled. For example, @option{-Wsuggest-final-types} is more effective +with link-time optimization. Some other warnings may not be issued at all unless optimization is enabled. While optimization -in general improves the efficacy of control and data flow sensitive -warnings, in some cases it may also cause false positives. +in general improves the efficacy of warnings about control and data-flow +problems, in some cases it may also cause false positives. @table @gcctabopt @opindex pedantic