return "";
}
-/* We only override this in bare-metal toolchain. */
-#ifdef RISCV_USE_CUSTOMISED_MULTI_LIB
-
/* Find last switch with the prefix, options are take last one in general,
return NULL if not found, and return the option value if found, it could
return empty string if the option has no value. */
return match_score + ok_count * 100;
}
+static const char *
+riscv_select_multilib_by_abi (
+ const std::string &riscv_current_arch_str,
+ const std::string &riscv_current_abi_str,
+ const riscv_subset_list *subset_list, const struct switchstr *switches,
+ int n_switches, const std::vector<riscv_multi_lib_info_t> &multilib_infos)
+{
+ for (size_t i = 0; i < multilib_infos.size (); ++i)
+ if (riscv_current_abi_str == multilib_infos[i].abi_str)
+ return xstrdup (multilib_infos[i].path.c_str ());
+
+ return NULL;
+}
+
+static const char *
+riscv_select_multilib (
+ const std::string &riscv_current_arch_str,
+ const std::string &riscv_current_abi_str,
+ const riscv_subset_list *subset_list, const struct switchstr *switches,
+ int n_switches, const std::vector<riscv_multi_lib_info_t> &multilib_infos)
+{
+ int match_score = 0;
+ int max_match_score = 0;
+ int best_match_multi_lib = -1;
+ /* Try to decision which set we should used. */
+ /* We have 3 level decision tree here, ABI, check input arch/ABI must
+ be superset of multi-lib arch, and other rest option checking. */
+ for (size_t i = 0; i < multilib_infos.size (); ++i)
+ {
+ /* Check ABI is same first. */
+ if (riscv_current_abi_str != multilib_infos[i].abi_str)
+ continue;
+
+ /* Found a potential compatible multi-lib setting!
+ Calculate the match score. */
+ match_score = subset_list->match_score (multilib_infos[i].subset_list);
+
+ /* Checking other cond in the multi-lib setting. */
+ match_score = riscv_check_conds (switches, n_switches, match_score,
+ multilib_infos[i].conds);
+
+ /* Record highest match score multi-lib setting. */
+ if (match_score > max_match_score)
+ {
+ best_match_multi_lib = i;
+ max_match_score = match_score;
+ }
+ }
+
+ if (best_match_multi_lib == -1)
+ {
+ riscv_no_matched_multi_lib = true;
+ return NULL;
+ }
+ else
+ return xstrdup (multilib_infos[best_match_multi_lib].path.c_str ());
+}
+
+#ifndef RISCV_USE_CUSTOMISED_MULTI_LIB
+#define RISCV_USE_CUSTOMISED_MULTI_LIB select_by_builtin
+#endif
+
/* Implement TARGET_COMPUTE_MULTILIB. */
static const char *
riscv_compute_multilib (
const char *multilib_exclusions ATTRIBUTE_UNUSED,
const char *multilib_reuse ATTRIBUTE_UNUSED)
{
+ enum riscv_multilib_select_kind select_kind = RISCV_USE_CUSTOMISED_MULTI_LIB;
+
+ if (select_kind == select_by_builtin)
+ return multilib_dir;
+
const char *p;
const char *this_path;
size_t this_path_len;
}
this_path_len = p - this_path;
- multilib_info.path = std::string (this_path, this_path_len);
+ const char *multi_os_dir_pos
+ = (const char *) memchr (this_path, ':', this_path_len);
+ if (multi_os_dir_pos)
+ multilib_info.path
+ = std::string (this_path, multi_os_dir_pos - this_path);
+ else
+ multilib_info.path = std::string (this_path, this_path_len);
option_conds.clear ();
/* Pasrse option check list into vector<string>.
p++;
}
- int match_score = 0;
- int max_match_score = 0;
- int best_match_multi_lib = -1;
- /* Try to decision which set we should used. */
- /* We have 3 level decision tree here, ABI, check input arch/ABI must
- be superset of multi-lib arch, and other rest option checking. */
- for (size_t i = 0; i < multilib_infos.size (); ++i)
+ switch (select_kind)
{
- /* Check ABI is same first. */
- if (riscv_current_abi_str != multilib_infos[i].abi_str)
- continue;
-
- /* Found a potential compatible multi-lib setting!
- Calculate the match score. */
- match_score = subset_list->match_score (multilib_infos[i].subset_list);
-
- /* Checking other cond in the multi-lib setting. */
- match_score = riscv_check_conds (switches,
- n_switches,
- match_score,
- multilib_infos[i].conds);
-
- /* Record highest match score multi-lib setting. */
- if (match_score > max_match_score)
- {
- best_match_multi_lib = i;
- max_match_score = match_score;
- }
- }
-
- if (best_match_multi_lib == -1)
- {
- riscv_no_matched_multi_lib = true;
- return multilib_dir;
+ case select_by_abi:
+ return riscv_select_multilib (riscv_current_arch_str,
+ riscv_current_abi_str, subset_list,
+ switches, n_switches, multilib_infos);
+ case select_by_abi_arch_cmodel:
+ return riscv_select_multilib_by_abi (riscv_current_arch_str,
+ riscv_current_abi_str, subset_list,
+ switches, n_switches,
+ multilib_infos);
+ case select_by_builtin:
+ gcc_unreachable ();
+ default:
+ gcc_unreachable ();
}
- else
- return xstrdup (multilib_infos[best_match_multi_lib].path.c_str ());
}
#undef TARGET_COMPUTE_MULTILIB
#define TARGET_COMPUTE_MULTILIB riscv_compute_multilib
-#endif
vec<const char *>
riscv_get_valid_option_values (int option_code,