aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorArthur Cohen <arthur.cohen@embecosm.com>2023-05-03 11:19:30 +0200
committerArthur Cohen <arthur.cohen@embecosm.com>2024-01-16 18:34:17 +0100
commitcf1287ee24c5c83b38737c50e3cd37ab62f3d279 (patch)
treef0dba879502610feb775a4901c72924786dba8cf /gcc
parent25c9921b1d9bd2c508c1ac3c89e2e192a17b6f8b (diff)
downloadgcc-cf1287ee24c5c83b38737c50e3cd37ab62f3d279.zip
gcc-cf1287ee24c5c83b38737c50e3cd37ab62f3d279.tar.gz
gcc-cf1287ee24c5c83b38737c50e3cd37ab62f3d279.tar.bz2
gccrs: builtin: Cleanup handling of builtin macros
This commit regroups information related to builtin macros in one place instead of spreading it over multiple files. It also adds a simple bi-directional hashmap in order to perform lookups from a key as well as a value. gcc/rust/ChangeLog: * ast/rust-macro.cc (builtin_macro_from_string): Move function. * ast/rust-macro.h (enum class): Move enum. (builtin_macro_from_string): Move function. * expand/rust-macro-builtins.cc (builtin_macro_from_string): New function. (make_macro_path_str): Use new bi-map. (parse_single_string_literal): Use new `BuiltinMacro` enum. (MacroBuiltin::include_bytes_handler): Likewise. (MacroBuiltin::include_str_handler): Likewise. (MacroBuiltin::compile_error_handler): Likewise. (MacroBuiltin::concat_handler): Likewise. (MacroBuiltin::env_handler): Likewise. (MacroBuiltin::include_handler): Likewise. (MacroBuiltin::sorry): New function. * expand/rust-macro-builtins.h (enum class): Move enum here. (builtin_macro_from_string): New function declaration. * resolve/rust-early-name-resolver.cc (EarlyNameResolver::visit): Use new function. * util/rust-hir-map.cc (Mappings::insert_macro_def): Remove old builtin macro map.
Diffstat (limited to 'gcc')
-rw-r--r--gcc/rust/ast/rust-macro.cc42
-rw-r--r--gcc/rust/ast/rust-macro.h23
-rw-r--r--gcc/rust/expand/rust-macro-builtins.cc153
-rw-r--r--gcc/rust/expand/rust-macro-builtins.h64
-rw-r--r--gcc/rust/resolve/rust-early-name-resolver.cc3
-rw-r--r--gcc/rust/util/rust-hir-map.cc22
6 files changed, 167 insertions, 140 deletions
diff --git a/gcc/rust/ast/rust-macro.cc b/gcc/rust/ast/rust-macro.cc
index b558969..f36feda 100644
--- a/gcc/rust/ast/rust-macro.cc
+++ b/gcc/rust/ast/rust-macro.cc
@@ -21,47 +21,5 @@
namespace Rust {
namespace AST {
-BuiltinMacro
-builtin_macro_from_string (const std::string &identifier)
-{
- if (identifier == "assert")
- return BuiltinMacro::Assert;
-
- if (identifier == "file")
- return BuiltinMacro::File;
-
- if (identifier == "line")
- return BuiltinMacro::Line;
-
- if (identifier == "column")
- return BuiltinMacro::Column;
-
- if (identifier == "include_bytes")
- return BuiltinMacro::IncludeBytes;
-
- if (identifier == "include_str")
- return BuiltinMacro::IncludeStr;
-
- if (identifier == "stringify")
- return BuiltinMacro::Stringify;
-
- if (identifier == "compile_error")
- return BuiltinMacro::CompileError;
-
- if (identifier == "concat")
- return BuiltinMacro::Concat;
-
- if (identifier == "env")
- return BuiltinMacro::Env;
-
- if (identifier == "cfg")
- return BuiltinMacro::Cfg;
-
- if (identifier == "include")
- return BuiltinMacro::Include;
-
- gcc_unreachable ();
-}
-
} // namespace AST
} // namespace Rust
diff --git a/gcc/rust/ast/rust-macro.h b/gcc/rust/ast/rust-macro.h
index 7216db8..b6349a7 100644
--- a/gcc/rust/ast/rust-macro.h
+++ b/gcc/rust/ast/rust-macro.h
@@ -25,6 +25,7 @@
#include "rust-location.h"
#include "rust-item.h"
#include "rust-make-unique.h"
+#include "rust-macro-builtins.h"
namespace Rust {
namespace AST {
@@ -578,28 +579,6 @@ protected:
}
};
-/**
- * All builtin macros possible
- */
-enum class BuiltinMacro
-{
- Assert,
- File,
- Line,
- Column,
- IncludeBytes,
- IncludeStr,
- Stringify,
- CompileError,
- Concat,
- Env,
- Cfg,
- Include
-};
-
-BuiltinMacro
-builtin_macro_from_string (const std::string &identifier);
-
/* AST node of a macro invocation, which is replaced by the macro result at
* compile time. This is technically a sum-type/tagged-union, which represents
* both classic macro invocations and builtin macro invocations. Regular macro
diff --git a/gcc/rust/expand/rust-macro-builtins.cc b/gcc/rust/expand/rust-macro-builtins.cc
index 29a8b8b..f0f1f8c 100644
--- a/gcc/rust/expand/rust-macro-builtins.cc
+++ b/gcc/rust/expand/rust-macro-builtins.cc
@@ -32,54 +32,91 @@
#include "bi-map.h"
namespace Rust {
+static const BiMap<std::string, BuiltinMacro> builtins = {{
+ {"assert", BuiltinMacro::Assert},
+ {"file", BuiltinMacro::File},
+ {"line", BuiltinMacro::Line},
+ {"column", BuiltinMacro::Column},
+ {"include_bytes", BuiltinMacro::IncludeBytes},
+ {"include_str", BuiltinMacro::IncludeStr},
+ {"stringify", BuiltinMacro::Stringify},
+ {"compile_error", BuiltinMacro::CompileError},
+ {"concat", BuiltinMacro::Concat},
+ {"env", BuiltinMacro::Env},
+ {"option_env", BuiltinMacro::OptionEnv},
+ {"cfg", BuiltinMacro::Cfg},
+ {"include", BuiltinMacro::Include},
+ {"format_args", BuiltinMacro::FormatArgs},
+ {"format_args_nl", BuiltinMacro::FormatArgsNl},
+ {"concat_idents", BuiltinMacro::ConcatIdents},
+ {"module_path", BuiltinMacro::ModulePath},
+ {"asm", BuiltinMacro::Asm},
+ {"llvm_asm", BuiltinMacro::LlvmAsm},
+ {"global_asm", BuiltinMacro::GlobalAsm},
+ {"log_syntax", BuiltinMacro::LogSyntax},
+ {"trace_macros", BuiltinMacro::TraceMacros},
+ {"test", BuiltinMacro::Test},
+ {"bench", BuiltinMacro::Bench},
+ {"test_case", BuiltinMacro::TestCase},
+ {"global_allocator", BuiltinMacro::GlobalAllocator},
+ {"cfg_accessible", BuiltinMacro::CfgAccessible},
+ {"RustcEncodable", BuiltinMacro::RustcDecodable},
+ {"RustcDecodable", BuiltinMacro::RustcEncodable},
+}};
+
+std::unordered_map<
+ std::string, std::function<AST::Fragment (Location, AST::MacroInvocData &)>>
+ MacroBuiltin::builtin_transcribers = {
+ {"assert", MacroBuiltin::assert_handler},
+ {"file", MacroBuiltin::file_handler},
+ {"line", MacroBuiltin::line_handler},
+ {"column", MacroBuiltin::column_handler},
+ {"include_bytes", MacroBuiltin::include_bytes_handler},
+ {"include_str", MacroBuiltin::include_str_handler},
+ {"stringify", MacroBuiltin::stringify_handler},
+ {"compile_error", MacroBuiltin::compile_error_handler},
+ {"concat", MacroBuiltin::concat_handler},
+ {"env", MacroBuiltin::env_handler},
+ {"cfg", MacroBuiltin::cfg_handler},
+ {"include", MacroBuiltin::include_handler},
+ /* Unimplemented macro builtins */
+ {"format_args", MacroBuiltin::sorry},
+ {"option_env", MacroBuiltin::sorry},
+ {"format_args_nl", MacroBuiltin::sorry},
+ {"concat_idents", MacroBuiltin::sorry},
+ {"module_path", MacroBuiltin::sorry},
+ {"asm", MacroBuiltin::sorry},
+ {"llvm_asm", MacroBuiltin::sorry},
+ {"global_asm", MacroBuiltin::sorry},
+ {"log_syntax", MacroBuiltin::sorry},
+ {"trace_macros", MacroBuiltin::sorry},
+ {"test", MacroBuiltin::sorry},
+ {"bench", MacroBuiltin::sorry},
+ {"test_case", MacroBuiltin::sorry},
+ {"global_allocator", MacroBuiltin::sorry},
+ {"cfg_accessible", MacroBuiltin::sorry},
+ {"RustcEncodable", MacroBuiltin::sorry},
+ {"RustcDecodable", MacroBuiltin::sorry},
+};
+
+// FIXME: This should return an Optional
+BuiltinMacro
+builtin_macro_from_string (const std::string &identifier)
+{
+ auto macro = builtins.lookup (identifier);
+ rust_assert (builtins.is_iter_ok (macro));
+
+ return macro->second;
+}
+
namespace {
std::string
-make_macro_path_str (AST::BuiltinMacro kind)
+make_macro_path_str (BuiltinMacro kind)
{
- std::string path_str;
+ auto str = builtins.lookup (kind);
+ rust_assert (builtins.is_iter_ok (str));
- switch (kind)
- {
- // TODO: Should this be a table lookup?
- case AST::BuiltinMacro::Assert:
- path_str = "assert";
- break;
- case AST::BuiltinMacro::File:
- path_str = "file";
- break;
- case AST::BuiltinMacro::Line:
- path_str = "line";
- break;
- case AST::BuiltinMacro::Column:
- path_str = "column";
- break;
- case AST::BuiltinMacro::IncludeBytes:
- path_str = "include_bytes";
- break;
- case AST::BuiltinMacro::IncludeStr:
- path_str = "include_str";
- break;
- case AST::BuiltinMacro::Stringify:
- path_str = "stringify";
- break;
- case AST::BuiltinMacro::CompileError:
- path_str = "compile_error";
- break;
- case AST::BuiltinMacro::Concat:
- path_str = "concat";
- break;
- case AST::BuiltinMacro::Env:
- path_str = "env";
- break;
- case AST::BuiltinMacro::Cfg:
- path_str = "cfg";
- break;
- case AST::BuiltinMacro::Include:
- path_str = "include";
- break;
- }
-
- return path_str;
+ return str->second;
}
static std::vector<std::unique_ptr<AST::MacroInvocation>>
@@ -116,7 +153,7 @@ make_string (Location locus, std::string value)
// TODO: Is this correct?
static AST::Fragment
make_eager_builtin_invocation (
- AST::BuiltinMacro kind, Location locus, AST::DelimTokenTree arguments,
+ BuiltinMacro kind, Location locus, AST::DelimTokenTree arguments,
std::vector<std::unique_ptr<AST::MacroInvocation>> &&pending_invocations)
{
auto path_str = make_macro_path_str (kind);
@@ -224,7 +261,7 @@ try_expand_many_expr (Parser<MacroInvocLexer> &parser,
but otherwise enforce that these are the only tokens. */
std::unique_ptr<AST::Expr>
-parse_single_string_literal (AST::BuiltinMacro kind,
+parse_single_string_literal (BuiltinMacro kind,
AST::DelimTokenTree &invoc_token_tree,
Location invoc_locus, MacroExpander *expander)
{
@@ -384,7 +421,7 @@ MacroBuiltin::include_bytes_handler (Location invoc_locus,
/* Get target filename from the macro invocation, which is treated as a path
relative to the include!-ing file (currently being compiled). */
auto lit_expr
- = parse_single_string_literal (AST::BuiltinMacro::IncludeBytes,
+ = parse_single_string_literal (BuiltinMacro::IncludeBytes,
invoc.get_delim_tok_tree (), invoc_locus,
invoc.get_expander ());
if (lit_expr == nullptr)
@@ -444,7 +481,7 @@ MacroBuiltin::include_str_handler (Location invoc_locus,
/* Get target filename from the macro invocation, which is treated as a path
relative to the include!-ing file (currently being compiled). */
auto lit_expr
- = parse_single_string_literal (AST::BuiltinMacro::IncludeStr,
+ = parse_single_string_literal (BuiltinMacro::IncludeStr,
invoc.get_delim_tok_tree (), invoc_locus,
invoc.get_expander ());
if (lit_expr == nullptr)
@@ -527,7 +564,7 @@ MacroBuiltin::compile_error_handler (Location invoc_locus,
AST::MacroInvocData &invoc)
{
auto lit_expr
- = parse_single_string_literal (AST::BuiltinMacro::CompileError,
+ = parse_single_string_literal (BuiltinMacro::CompileError,
invoc.get_delim_tok_tree (), invoc_locus,
invoc.get_expander ());
if (lit_expr == nullptr)
@@ -605,8 +642,7 @@ MacroBuiltin::concat_handler (Location invoc_locus, AST::MacroInvocData &invoc)
auto pending_invocations = check_for_eager_invocations (expanded_expr);
if (!pending_invocations.empty ())
- return make_eager_builtin_invocation (AST::BuiltinMacro::Concat,
- invoc_locus,
+ return make_eager_builtin_invocation (BuiltinMacro::Concat, invoc_locus,
invoc.get_delim_tok_tree (),
std::move (pending_invocations));
@@ -672,7 +708,7 @@ MacroBuiltin::env_handler (Location invoc_locus, AST::MacroInvocData &invoc)
auto pending = check_for_eager_invocations (expanded_expr);
if (!pending.empty ())
- return make_eager_builtin_invocation (AST::BuiltinMacro::Env, invoc_locus,
+ return make_eager_builtin_invocation (BuiltinMacro::Env, invoc_locus,
invoc_token_tree,
std::move (pending));
@@ -770,7 +806,7 @@ MacroBuiltin::include_handler (Location invoc_locus, AST::MacroInvocData &invoc)
/* Get target filename from the macro invocation, which is treated as a path
relative to the include!-ing file (currently being compiled). */
auto lit_expr
- = parse_single_string_literal (AST::BuiltinMacro::Include,
+ = parse_single_string_literal (BuiltinMacro::Include,
invoc.get_delim_tok_tree (), invoc_locus,
invoc.get_expander ());
if (lit_expr == nullptr)
@@ -877,6 +913,15 @@ MacroBuiltin::stringify_handler (Location invoc_locus,
auto token
= make_token (Token::make_string (invoc_locus, std::move (content)));
return AST::Fragment ({node}, std::move (token));
-} // namespace Rust
+}
+
+AST::Fragment
+MacroBuiltin::sorry (Location invoc_locus, AST::MacroInvocData &invoc)
+{
+ rust_sorry_at (invoc_locus, "unimplemented builtin macro: %qs",
+ invoc.get_path ().as_string ().c_str ());
+
+ return AST::Fragment::create_error ();
+}
} // namespace Rust
diff --git a/gcc/rust/expand/rust-macro-builtins.h b/gcc/rust/expand/rust-macro-builtins.h
index bd4f1f9..10a38d7 100644
--- a/gcc/rust/expand/rust-macro-builtins.h
+++ b/gcc/rust/expand/rust-macro-builtins.h
@@ -23,6 +23,51 @@
#include "rust-ast-fragment.h"
#include "rust-location.h"
+namespace Rust {
+
+// FIXME: Add a BuiltinMacro class which contains a name (or should it?), a
+// transcriber and extra info if necessary
+// then make a global map<string, BuiltinMacro>
+
+/**
+ * All builtin macros possible
+ */
+enum class BuiltinMacro
+{
+ Assert,
+ File,
+ Line,
+ Column,
+ IncludeBytes,
+ IncludeStr,
+ Stringify,
+ CompileError,
+ Concat,
+ Env,
+ OptionEnv,
+ Cfg,
+ Include,
+ FormatArgs,
+ FormatArgsNl,
+ ConcatIdents,
+ ModulePath,
+ Asm,
+ LlvmAsm,
+ GlobalAsm,
+ LogSyntax,
+ TraceMacros,
+ Test,
+ Bench,
+ TestCase,
+ GlobalAllocator,
+ CfgAccessible,
+ RustcDecodable,
+ RustcEncodable,
+};
+
+BuiltinMacro
+builtin_macro_from_string (const std::string &identifier);
+
/**
* This class provides a list of builtin macros implemented by the compiler.
* The functions defined are called "builtin transcribers" in that they replace
@@ -59,11 +104,13 @@
* This map is built as a static variable in the `insert_macro_def()` method
* of the `Mappings` class.
*/
-
-namespace Rust {
class MacroBuiltin
{
public:
+ static std::unordered_map<
+ std::string, std::function<AST::Fragment (Location, AST::MacroInvocData &)>>
+ builtin_transcribers;
+
static AST::Fragment assert_handler (Location invoc_locus,
AST::MacroInvocData &invoc);
@@ -99,7 +146,20 @@ public:
static AST::Fragment line_handler (Location invoc_locus,
AST::MacroInvocData &invoc);
+
+ static AST::Fragment sorry (Location invoc_locus, AST::MacroInvocData &invoc);
};
} // namespace Rust
+namespace std {
+template <> struct hash<Rust::BuiltinMacro>
+{
+ size_t operator() (const Rust::BuiltinMacro &macro) const noexcept
+ {
+ return hash<std::underlying_type<Rust::BuiltinMacro>::type> () (
+ static_cast<std::underlying_type<Rust::BuiltinMacro>::type> (macro));
+ }
+};
+} // namespace std
+
#endif // RUST_MACRO_BUILTINS_H
diff --git a/gcc/rust/resolve/rust-early-name-resolver.cc b/gcc/rust/resolve/rust-early-name-resolver.cc
index 6e869d6..145b393 100644
--- a/gcc/rust/resolve/rust-early-name-resolver.cc
+++ b/gcc/rust/resolve/rust-early-name-resolver.cc
@@ -19,6 +19,7 @@
#include "rust-early-name-resolver.h"
#include "rust-ast-full.h"
#include "rust-name-resolver.h"
+#include "rust-macro-builtins.h"
namespace Rust {
namespace Resolver {
@@ -873,7 +874,7 @@ EarlyNameResolver::visit (AST::MacroInvocation &invoc)
if (is_builtin)
{
auto builtin_kind
- = AST::builtin_macro_from_string (rules_def->get_rule_name ());
+ = builtin_macro_from_string (rules_def->get_rule_name ());
invoc.map_to_builtin (builtin_kind);
}
diff --git a/gcc/rust/util/rust-hir-map.cc b/gcc/rust/util/rust-hir-map.cc
index 8d001fd..5c711ca 100644
--- a/gcc/rust/util/rust-hir-map.cc
+++ b/gcc/rust/util/rust-hir-map.cc
@@ -868,23 +868,6 @@ Mappings::iterate_trait_items (
void
Mappings::insert_macro_def (AST::MacroRulesDefinition *macro)
{
- static std::map<
- std::string, std::function<AST::Fragment (Location, AST::MacroInvocData &)>>
- builtin_macros = {
- {"assert", MacroBuiltin::assert_handler},
- {"file", MacroBuiltin::file_handler},
- {"line", MacroBuiltin::line_handler},
- {"column", MacroBuiltin::column_handler},
- {"include_bytes", MacroBuiltin::include_bytes_handler},
- {"include_str", MacroBuiltin::include_str_handler},
- {"stringify", MacroBuiltin::stringify_handler},
- {"compile_error", MacroBuiltin::compile_error_handler},
- {"concat", MacroBuiltin::concat_handler},
- {"env", MacroBuiltin::env_handler},
- {"cfg", MacroBuiltin::cfg_handler},
- {"include", MacroBuiltin::include_handler},
- };
-
auto outer_attrs = macro->get_outer_attrs ();
bool should_be_builtin
= std::any_of (outer_attrs.begin (), outer_attrs.end (),
@@ -893,8 +876,9 @@ Mappings::insert_macro_def (AST::MacroRulesDefinition *macro)
});
if (should_be_builtin)
{
- auto builtin = builtin_macros.find (macro->get_rule_name ());
- if (builtin != builtin_macros.end ())
+ auto builtin
+ = MacroBuiltin::builtin_transcribers.find (macro->get_rule_name ());
+ if (builtin != MacroBuiltin::builtin_transcribers.end ())
macro->set_builtin_transcriber (builtin->second);
else
rust_error_at (macro->get_locus (),