From 7e949f08700b077b78e955c653eb4e9455027101 Mon Sep 17 00:00:00 2001 From: Tom Tromey Date: Thu, 29 Feb 2024 13:54:19 -0700 Subject: Implement Ada 2022 delta aggregates Ada 2022 includes a "delta aggregates" feature that can sometimes simplify aggregate creation. This patch implements this feature for GDB. --- gdb/ada-lang.c | 42 ++++++++++++++++++++++++++++++++++++++---- 1 file changed, 38 insertions(+), 4 deletions(-) (limited to 'gdb/ada-lang.c') diff --git a/gdb/ada-lang.c b/gdb/ada-lang.c index 2a90495..493ef3b 100644 --- a/gdb/ada-lang.c +++ b/gdb/ada-lang.c @@ -9323,10 +9323,9 @@ check_objfile (const std::unique_ptr &comp, return comp->uses_objfile (objfile); } -/* Assign the result of evaluating ARG starting at *POS to the INDEXth - component of LHS (a simple array or a record). Does not modify the - inferior's memory, nor does it modify LHS (unless LHS == - CONTAINER). */ +/* Assign the result of evaluating ARG to the INDEXth component of LHS + (a simple array or a record). Does not modify the inferior's + memory, nor does it modify LHS (unless LHS == CONTAINER). */ static void assign_component (struct value *container, struct value *lhs, LONGEST index, @@ -9363,6 +9362,8 @@ assign_component (struct value *container, struct value *lhs, LONGEST index, bool ada_aggregate_component::uses_objfile (struct objfile *objfile) { + if (m_base != nullptr && m_base->uses_objfile (objfile)) + return true; for (const auto &item : m_components) if (item->uses_objfile (objfile)) return true; @@ -9373,6 +9374,11 @@ void ada_aggregate_component::dump (ui_file *stream, int depth) { gdb_printf (stream, _("%*sAggregate\n"), depth, ""); + if (m_base != nullptr) + { + gdb_printf (stream, _("%*swith delta\n"), depth + 1, ""); + m_base->dump (stream, depth + 2); + } for (const auto &item : m_components) item->dump (stream, depth + 1); } @@ -9383,12 +9389,40 @@ ada_aggregate_component::assign (struct value *container, std::vector &indices, LONGEST low, LONGEST high) { + if (m_base != nullptr) + { + value *base = m_base->evaluate (nullptr, exp, EVAL_NORMAL); + if (ada_is_direct_array_type (base->type ())) + base = ada_coerce_to_simple_array (base); + if (!types_deeply_equal (container->type (), base->type ())) + error (_("Type mismatch in delta aggregate")); + value_assign_to_component (container, container, base); + } + for (auto &item : m_components) item->assign (container, lhs, exp, indices, low, high); } /* See ada-exp.h. */ +ada_aggregate_component::ada_aggregate_component + (operation_up &&base, std::vector &&components) + : m_base (std::move (base)), + m_components (std::move (components)) +{ + for (const auto &component : m_components) + if (dynamic_cast (component.get ()) + != nullptr) + { + /* It's invalid and nonsensical to have 'others => ...' with a + delta aggregate. It was simpler to enforce this + restriction here as opposed to in the parser. */ + error (_("'others' invalid in delta aggregate")); + } +} + +/* See ada-exp.h. */ + value * ada_aggregate_operation::assign_aggregate (struct value *container, struct value *lhs, -- cgit v1.1