Commit d7706b0a by Kito Cheng Committed by Kito Cheng

RISC-V: Refine riscv_parse_arch_string

 - Generalize logic for translating arch to internal flags, this patch
   is infrastructure for supporing sub-extension parsing.

gcc/ChangeLog

	* common/config/riscv/riscv-common.c (opt_var_ref_t): New.
	(riscv_ext_flag_table_t): New.
	(riscv_ext_flag_table): New.
	(riscv_parse_arch_string): Pass gcc_options* instead of
	&opts->x_target_flags only, and using riscv_arch_option_table to
	setup flags.
	(riscv_handle_option): Update argument for riscv_parse_arch_string.
	(riscv_expand_arch): Ditto.
	(riscv_expand_arch_from_cpu): Ditto.
parent b1b56733
...@@ -618,44 +618,64 @@ riscv_arch_str (bool version_p) ...@@ -618,44 +618,64 @@ riscv_arch_str (bool version_p)
return std::string(); return std::string();
} }
/* Type for pointer to member of gcc_options. */
typedef int (gcc_options::*opt_var_ref_t);
/* Types for recording extension to internal flag. */
struct riscv_ext_flag_table_t {
const char *ext;
opt_var_ref_t var_ref;
int mask;
};
/* Mapping table between extension to internal flag. */
static const riscv_ext_flag_table_t riscv_ext_flag_table[] =
{
{"e", &gcc_options::x_target_flags, MASK_RVE},
{"m", &gcc_options::x_target_flags, MASK_MUL},
{"a", &gcc_options::x_target_flags, MASK_ATOMIC},
{"f", &gcc_options::x_target_flags, MASK_HARD_FLOAT},
{"d", &gcc_options::x_target_flags, MASK_DOUBLE_FLOAT},
{"c", &gcc_options::x_target_flags, MASK_RVC},
{NULL, NULL, 0}
};
/* Parse a RISC-V ISA string into an option mask. Must clear or set all arch /* Parse a RISC-V ISA string into an option mask. Must clear or set all arch
dependent mask bits, in case more than one -march string is passed. */ dependent mask bits, in case more than one -march string is passed. */
static void static void
riscv_parse_arch_string (const char *isa, int *flags, location_t loc) riscv_parse_arch_string (const char *isa,
struct gcc_options *opts,
location_t loc)
{ {
riscv_subset_list *subset_list; riscv_subset_list *subset_list;
subset_list = riscv_subset_list::parse (isa, loc); subset_list = riscv_subset_list::parse (isa, loc);
if (!subset_list) if (!subset_list)
return; return;
if (subset_list->xlen () == 32) if (opts)
*flags &= ~MASK_64BIT; {
else if (subset_list->xlen () == 64) const riscv_ext_flag_table_t *arch_ext_flag_tab;
*flags |= MASK_64BIT; /* Clean up target flags before we set. */
for (arch_ext_flag_tab = &riscv_ext_flag_table[0];
*flags &= ~MASK_RVE; arch_ext_flag_tab->ext;
if (subset_list->lookup ("e")) ++arch_ext_flag_tab)
*flags |= MASK_RVE; opts->*arch_ext_flag_tab->var_ref &= ~arch_ext_flag_tab->mask;
*flags &= ~MASK_MUL; if (subset_list->xlen () == 32)
if (subset_list->lookup ("m")) opts->x_target_flags &= ~MASK_64BIT;
*flags |= MASK_MUL; else if (subset_list->xlen () == 64)
opts->x_target_flags |= MASK_64BIT;
*flags &= ~MASK_ATOMIC;
if (subset_list->lookup ("a"))
*flags |= MASK_ATOMIC; for (arch_ext_flag_tab = &riscv_ext_flag_table[0];
arch_ext_flag_tab->ext;
*flags &= ~(MASK_HARD_FLOAT | MASK_DOUBLE_FLOAT); ++arch_ext_flag_tab)
if (subset_list->lookup ("f")) {
*flags |= MASK_HARD_FLOAT; if (subset_list->lookup (arch_ext_flag_tab->ext))
opts->*arch_ext_flag_tab->var_ref |= arch_ext_flag_tab->mask;
if (subset_list->lookup ("d")) }
*flags |= MASK_DOUBLE_FLOAT; }
*flags &= ~MASK_RVC;
if (subset_list->lookup ("c"))
*flags |= MASK_RVC;
if (current_subset_list) if (current_subset_list)
delete current_subset_list; delete current_subset_list;
...@@ -689,7 +709,7 @@ riscv_handle_option (struct gcc_options *opts, ...@@ -689,7 +709,7 @@ riscv_handle_option (struct gcc_options *opts,
switch (decoded->opt_index) switch (decoded->opt_index)
{ {
case OPT_march_: case OPT_march_:
riscv_parse_arch_string (decoded->arg, &opts->x_target_flags, loc); riscv_parse_arch_string (decoded->arg, opts, loc);
return true; return true;
case OPT_mcpu_: case OPT_mcpu_:
...@@ -710,9 +730,8 @@ riscv_expand_arch (int argc ATTRIBUTE_UNUSED, ...@@ -710,9 +730,8 @@ riscv_expand_arch (int argc ATTRIBUTE_UNUSED,
const char **argv) const char **argv)
{ {
gcc_assert (argc == 1); gcc_assert (argc == 1);
int flags;
location_t loc = UNKNOWN_LOCATION; location_t loc = UNKNOWN_LOCATION;
riscv_parse_arch_string (argv[0], &flags, loc); riscv_parse_arch_string (argv[0], NULL, loc);
const std::string arch = riscv_arch_str (false); const std::string arch = riscv_arch_str (false);
if (arch.length()) if (arch.length())
return xasprintf ("-march=%s", arch.c_str()); return xasprintf ("-march=%s", arch.c_str());
...@@ -760,9 +779,8 @@ riscv_expand_arch_from_cpu (int argc ATTRIBUTE_UNUSED, ...@@ -760,9 +779,8 @@ riscv_expand_arch_from_cpu (int argc ATTRIBUTE_UNUSED,
arch_str = cpu->arch; arch_str = cpu->arch;
location_t loc = UNKNOWN_LOCATION; location_t loc = UNKNOWN_LOCATION;
int flags;
riscv_parse_arch_string (arch_str, &flags, loc); riscv_parse_arch_string (arch_str, NULL, loc);
const std::string arch = riscv_arch_str (false); const std::string arch = riscv_arch_str (false);
return xasprintf ("-march=%s", arch.c_str()); return xasprintf ("-march=%s", arch.c_str());
} }
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment