--- /dev/null
+// Copyright (C) 2020-2023 Free Software Foundation, Inc.
+
+// This file is part of GCC.
+
+// GCC is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 3, or (at your option) any later
+// version.
+
+// GCC is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
+// for more details.
+
+// You should have received a copy of the GNU General Public License
+// along with GCC; see the file COPYING3. If not see
+// <http://www.gnu.org/licenses/>.
+
+#include "rust-derive-copy.h"
+#include "rust-ast-full.h"
+
+namespace Rust {
+namespace AST {
+
+DeriveCopy::DeriveCopy (Location loc)
+ : loc (loc), builder (AstBuilder (loc)), expanded (nullptr)
+{}
+
+std::unique_ptr<AST::Item>
+DeriveCopy::go (Item &item)
+{
+ item.accept_vis (*this);
+
+ rust_assert (expanded);
+
+ return std::move (expanded);
+}
+
+std::unique_ptr<Item>
+DeriveCopy::copy_impl (std::string name)
+{
+ // `$crate::core::marker::Copy` instead
+ auto segments = std::vector<std::unique_ptr<TypePathSegment>> ();
+ segments.emplace_back (builder.type_path_segment ("Copy"));
+ auto copy = TypePath (std::move (segments), loc);
+
+ return std::unique_ptr<Item> (
+ new TraitImpl (copy, /* unsafe */ false,
+ /* exclam */ false, /* trait items */ {},
+ /* generics */ {}, builder.single_type_path (name),
+ WhereClause::create_empty (), Visibility::create_private (),
+ {}, {}, loc));
+}
+
+void
+DeriveCopy::visit_struct (StructStruct &item)
+{
+ expanded = copy_impl (item.get_struct_name ());
+}
+
+void
+DeriveCopy::visit_tuple (TupleStruct &item)
+{
+ expanded = copy_impl (item.get_struct_name ());
+}
+
+void
+DeriveCopy::visit_enum (Enum &item)
+{
+ expanded = copy_impl (item.get_identifier ());
+}
+
+void
+DeriveCopy::visit_union (Union &item)
+{
+ expanded = copy_impl (item.get_identifier ());
+}
+
+} // namespace AST
+} // namespace Rust
--- /dev/null
+// Copyright (C) 2020-2023 Free Software Foundation, Inc.
+
+// This file is part of GCC.
+
+// GCC is free software; you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 3, or (at your option) any later
+// version.
+
+// GCC is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
+// for more details.
+
+// You should have received a copy of the GNU General Public License
+// along with GCC; see the file COPYING3. If not see
+// <http://www.gnu.org/licenses/>.
+
+#ifndef RUST_DERIVE_COPY_H
+#define RUST_DERIVE_COPY_H
+
+#include "rust-derive.h"
+#include "rust-ast-builder.h"
+
+namespace Rust {
+namespace AST {
+class DeriveCopy : DeriveVisitor
+{
+public:
+ DeriveCopy (Location loc);
+
+ std::unique_ptr<Item> go (Item &);
+
+private:
+ Location loc;
+ AstBuilder builder;
+ std::unique_ptr<Item> expanded;
+
+ /**
+ * Create the Copy impl block for a type. These impl blocks are very simple as
+ * Copy is just a marker trait.
+ *
+ * impl Copy for <type> {}
+ */
+ std::unique_ptr<Item> copy_impl (std::string name);
+
+ virtual void visit_struct (StructStruct &item);
+ virtual void visit_tuple (TupleStruct &item);
+ virtual void visit_enum (Enum &item);
+ virtual void visit_union (Union &item);
+};
+
+} // namespace AST
+} // namespace Rust
+
+#endif // !RUST_DERIVE_COPY_H