* [PATCH] xtensa: add dynconfig option for ld/gas
@ 2023-07-20 14:39 Alexey Lapshin
2023-07-20 14:40 ` Alexey Lapshin
0 siblings, 1 reply; 3+ messages in thread
From: Alexey Lapshin @ 2023-07-20 14:39 UTC (permalink / raw)
To: binutils; +Cc: Alexey Gerenkov, Ivan Grokhotkov, jcmvbkbc
bfd/
* bfd/xtensa-dynconfig.c: Add xtensa_dynconfig_file variable.
gas/
* gas/config/tc-xtensa.c: Add dynconfig option.
ld/
* ld/emultempl/xtensaelf.em: Add dynconfig option.
---
bfd/xtensa-dynconfig.c | 57 +++++++++++++++++++++++++++++++++++++--
gas/config/tc-xtensa.c | 29 ++++++++++++++++++--
ld/emultempl/xtensaelf.em | 10 +++++++
3 files changed, 92 insertions(+), 4 deletions(-)
diff --git a/bfd/xtensa-dynconfig.c b/bfd/xtensa-dynconfig.c
index ebf4098f59c..0140936e98e 100644
--- a/bfd/xtensa-dynconfig.c
+++ b/bfd/xtensa-dynconfig.c
@@ -20,6 +20,7 @@
#include "sysdep.h"
#include "bfd.h"
#include "libbfd.h"
+#include "libiberty.h"
#define XTENSA_CONFIG_DEFINITION
#include "xtensa-config.h"
@@ -64,6 +65,57 @@ dlerror (void)
#define CONFIG_ENV_NAME "XTENSA_GNU_CONFIG"
+/* this variable can be changed with input option for gas/ld */
+const char *xtensa_dynconfig_file = "";
+
+#ifdef BFD_SUPPORTS_PLUGINS
+
+static char *get_xtensa_dynconfig_file (void)
+{
+ const char *xtensa_dynconfig_env = getenv (CONFIG_ENV_NAME);
+ if (!strlen (xtensa_dynconfig_file))
+ {
+ if (xtensa_dynconfig_env && !strlen (lbasename (xtensa_dynconfig_env)))
+ {
+ /* XTENSA_GNU_CONFIG has directory path, but dynconfig file is not set */
+ return NULL;
+ }
+ else if (xtensa_dynconfig_env)
+ {
+ /* XTENSA_GNU_CONFIG has filepath */
+ return xstrdup (xtensa_dynconfig_env);
+ }
+ /* dynconfig is not set */
+ return NULL;
+ }
+ if (!xtensa_dynconfig_env)
+ {
+ /* XTENSA_GNU_CONFIG has filepath */
+ return xstrdup (xtensa_dynconfig_file);
+ }
+ if (!strlen (lbasename (xtensa_dynconfig_env)))
+ {
+ /* XTENSA_GNU_CONFIG has directory path and dynconfig file is set */
+ const size_t len = strlen (xtensa_dynconfig_env) +
+ strlen (xtensa_dynconfig_file) + 1;
+ char *path = ( char *) xmalloc (len);
+ strcpy (path, xtensa_dynconfig_env);
+ strcat (path, xtensa_dynconfig_file);
+ return path;
+ }
+ if (strcmp (lbasename (xtensa_dynconfig_env),
+ lbasename (xtensa_dynconfig_file)))
+ {
+ _bfd_error_handler (_("Both %s and \"-dynconfig=\" specified but pointed different files: \"%s\" \"%s\""),
+ CONFIG_ENV_NAME, xtensa_dynconfig_env, xtensa_dynconfig_file);
+ abort ();
+ }
+ /* XTENSA_GNU_CONFIG and mdynconfig option point to the same file */
+ return xstrdup (xtensa_dynconfig_env);
+}
+
+#endif /* BFD_SUPPORTS_PLUGINS */
+
const void *xtensa_load_config (const char *name ATTRIBUTE_UNUSED,
const void *no_plugin_def,
const void *no_name_def ATTRIBUTE_UNUSED)
@@ -75,12 +127,13 @@ const void *xtensa_load_config (const char *name ATTRIBUTE_UNUSED,
if (!init)
{
- const char *path = getenv (CONFIG_ENV_NAME);
+ char *path = get_xtensa_dynconfig_file();
init = 1;
if (!path)
return no_plugin_def;
handle = dlopen (path, RTLD_LAZY);
+ free (path);
if (!handle)
{
_bfd_error_handler (_("%s is defined but could not be loaded: %s"),
@@ -107,7 +160,7 @@ const void *xtensa_load_config (const char *name ATTRIBUTE_UNUSED,
#else
if (!init)
{
- const char *path = getenv (CONFIG_ENV_NAME);
+ const char *path = strcmp(xtensa_dynconfig_file, "") ? xtensa_dynconfig_file : getenv (CONFIG_ENV_NAME);
init = 1;
if (path)
diff --git a/gas/config/tc-xtensa.c b/gas/config/tc-xtensa.c
index 550c8256e3f..d9ba8bc8690 100644
--- a/gas/config/tc-xtensa.c
+++ b/gas/config/tc-xtensa.c
@@ -733,6 +733,8 @@ enum
option_abi_windowed,
option_abi_call0,
+
+ option_dynconfig,
};
const char *md_shortopts = "";
@@ -817,6 +819,7 @@ struct option md_longopts[] =
{ "abi-windowed", no_argument, NULL, option_abi_windowed },
{ "abi-call0", no_argument, NULL, option_abi_call0 },
+ { "dynconfig=", required_argument, NULL, option_dynconfig },
{ NULL, no_argument, NULL, 0 }
};
@@ -1053,6 +1056,12 @@ md_parse_option (int c, const char *arg)
elf32xtensa_abi = XTHAL_ABI_CALL0;
return 1;
+ case option_dynconfig:
+ {
+ /* Applied in xtensa_init() */
+ return 1;
+ }
+
default:
return 0;
}
@@ -1087,7 +1096,9 @@ Xtensa options:\n\
--[no-]separate-prop-tables\n\
[Do not] place Xtensa property records into\n\
individual property sections for each section.\n\
- Default is to generate single property section.\n", stream);
+ Default is to generate single property section.\n\
+ --dynconfig=<file>\n\
+ Use xtensa dynconfig options\n", stream);
}
\f
@@ -5268,8 +5279,22 @@ xg_init_global_config (void)
}
void
-xtensa_init (int argc ATTRIBUTE_UNUSED, char **argv ATTRIBUTE_UNUSED)
+xtensa_init (int argc, char **argv)
{
+ /* This function is called before AS arguments parsed.
+ * So, dynconfig file must be set first.
+ */
+ int i;
+ const char * const dynconfig_opt = "--dynconfig=";
+ for (i = 1; i < argc; i++)
+ {
+ if (!strncmp (dynconfig_opt, argv[i], strlen(dynconfig_opt)))
+ {
+ extern const char* xtensa_dynconfig_file;
+ xtensa_dynconfig_file = &argv[i][strlen(dynconfig_opt)];
+ break;
+ }
+ }
xg_init_global_config ();
}
diff --git a/ld/emultempl/xtensaelf.em b/ld/emultempl/xtensaelf.em
index 4cb9bda8f92..615bde5655b 100644
--- a/ld/emultempl/xtensaelf.em
+++ b/ld/emultempl/xtensaelf.em
@@ -1930,6 +1930,7 @@ PARSE_AND_LIST_PROLOGUE='
#define OPTION_NO_LITERAL_MOVEMENT (OPTION_LITERAL_MOVEMENT + 1)
#define OPTION_ABI_WINDOWED (OPTION_NO_LITERAL_MOVEMENT + 1)
#define OPTION_ABI_CALL0 (OPTION_ABI_WINDOWED + 1)
+#define OPTION_DYNCONFIG (OPTION_ABI_CALL0 + 1)
extern int elf32xtensa_size_opt;
extern int elf32xtensa_no_literal_movement;
extern int elf32xtensa_abi;
@@ -1941,6 +1942,7 @@ PARSE_AND_LIST_LONGOPTS='
{ "no-literal-movement", no_argument, NULL, OPTION_NO_LITERAL_MOVEMENT},
{ "abi-windowed", no_argument, NULL, OPTION_ABI_WINDOWED},
{ "abi-call0", no_argument, NULL, OPTION_ABI_CALL0},
+ { "dynconfig=", required_argument, NULL, OPTION_DYNCONFIG},
'
PARSE_AND_LIST_OPTIONS='
@@ -1951,6 +1953,8 @@ PARSE_AND_LIST_OPTIONS='
--abi-windowed Choose windowed ABI for the output object\n"));
fprintf (file, _("\
--abi-call0 Choose call0 ABI for the output object\n"));
+ fprintf (file, _("\
+ --dynconfig=FILE Choose xtensa dynconfig file\n"));
'
PARSE_AND_LIST_ARGS_CASES='
@@ -1969,6 +1973,12 @@ PARSE_AND_LIST_ARGS_CASES='
case OPTION_ABI_CALL0:
elf32xtensa_abi = XTHAL_ABI_CALL0;
break;
+ case OPTION_DYNCONFIG:
+ {
+ extern const char* xtensa_dynconfig_file;
+ xtensa_dynconfig_file = optarg;
+ break;
+ }
'
# Replace some of the standard ELF functions with our own versions.
--
2.34.1
^ permalink raw reply [flat|nested] 3+ messages in thread
* Re: [PATCH] xtensa: add dynconfig option for ld/gas
2023-07-20 14:39 [PATCH] xtensa: add dynconfig option for ld/gas Alexey Lapshin
@ 2023-07-20 14:40 ` Alexey Lapshin
2024-04-01 13:01 ` [PATCH v2] " Alexey Lapshin
0 siblings, 1 reply; 3+ messages in thread
From: Alexey Lapshin @ 2023-07-20 14:40 UTC (permalink / raw)
To: binutils; +Cc: Alexey Gerenkov, Ivan Grokhotkov, jcmvbkbc
This patch is related to https://gcc.gnu.org/pipermail/gcc-patches/2023-July/625080.html
^ permalink raw reply [flat|nested] 3+ messages in thread
* [PATCH v2] xtensa: add dynconfig option for ld/gas
2023-07-20 14:40 ` Alexey Lapshin
@ 2024-04-01 13:01 ` Alexey Lapshin
0 siblings, 0 replies; 3+ messages in thread
From: Alexey Lapshin @ 2024-04-01 13:01 UTC (permalink / raw)
To: binutils; +Cc: Alexey Gerenkov, Ivan Grokhotkov, jcmvbkbc
This needs to build xtensa multilib. Multilib can not operate with
environment variables but with compile options.
bfd/
* bfd/xtensa-dynconfig.c: Add xtensa_dynconfig_file variable.
gas/
* gas/config/tc-xtensa.c: Add dynconfig option.
ld/
* ld/emultempl/xtensaelf.em: Add dynconfig option.
---
bfd/xtensa-dynconfig.c | 70 ++++++++++++++++++++++++++++++++++++--
gas/config/tc-xtensa.c | 16 ++++++++-
include/xtensa-dynconfig.h | 3 ++
ld/emultempl/xtensaelf.em | 10 ++++++
ld/ldlex.h | 1 +
5 files changed, 97 insertions(+), 3 deletions(-)
diff --git a/bfd/xtensa-dynconfig.c b/bfd/xtensa-dynconfig.c
index 843f376326b..bd47798047e 100644
--- a/bfd/xtensa-dynconfig.c
+++ b/bfd/xtensa-dynconfig.c
@@ -20,6 +20,7 @@
#include "sysdep.h"
#include "bfd.h"
#include "libbfd.h"
+#include "libiberty.h"
#define XTENSA_CONFIG_DEFINITION
#include "xtensa-config.h"
@@ -64,6 +65,70 @@ dlerror (void)
#define CONFIG_ENV_NAME "XTENSA_GNU_CONFIG"
+/* this variable can be changed with input option for gas/ld */
+const char *xtensa_dynconfig_file = "";
+
+void xtensa_set_dynconfig_from_argv(int argc, char **argv)
+{
+ const char * const dynconfig_opt = "--dynconfig=";
+ for (int i = 1; i < argc; i++)
+ {
+ if (!strncmp (dynconfig_opt, argv[i], strlen(dynconfig_opt)))
+ {
+ xtensa_dynconfig_file = &argv[i][strlen(dynconfig_opt)];
+ break;
+ }
+ }
+}
+
+#ifdef BFD_SUPPORTS_PLUGINS
+
+static char *get_xtensa_dynconfig_file (void)
+{
+ const char *xtensa_dynconfig_env = getenv (CONFIG_ENV_NAME);
+ if (!strlen (xtensa_dynconfig_file))
+ {
+ if (xtensa_dynconfig_env && !strlen (lbasename (xtensa_dynconfig_env)))
+ {
+ /* XTENSA_GNU_CONFIG has directory path, but dynconfig file is not set */
+ return NULL;
+ }
+ else if (xtensa_dynconfig_env)
+ {
+ /* XTENSA_GNU_CONFIG has filepath */
+ return xstrdup (xtensa_dynconfig_env);
+ }
+ /* dynconfig is not set */
+ return NULL;
+ }
+ if (!xtensa_dynconfig_env)
+ {
+ /* XTENSA_GNU_CONFIG has filepath */
+ return xstrdup (xtensa_dynconfig_file);
+ }
+ if (!strlen (lbasename (xtensa_dynconfig_env)))
+ {
+ /* XTENSA_GNU_CONFIG has directory path and dynconfig file is set */
+ const size_t len = strlen (xtensa_dynconfig_env) +
+ strlen (xtensa_dynconfig_file) + 1;
+ char *path = ( char *) xmalloc (len);
+ strcpy (path, xtensa_dynconfig_env);
+ strcat (path, xtensa_dynconfig_file);
+ return path;
+ }
+ if (strcmp (lbasename (xtensa_dynconfig_env),
+ lbasename (xtensa_dynconfig_file)))
+ {
+ _bfd_error_handler (_("Both %s and \"-dynconfig=\" specified but pointed different files: \"%s\" \"%s\""),
+ CONFIG_ENV_NAME, xtensa_dynconfig_env, xtensa_dynconfig_file);
+ abort ();
+ }
+ /* XTENSA_GNU_CONFIG and mdynconfig option point to the same file */
+ return xstrdup (xtensa_dynconfig_env);
+}
+
+#endif /* BFD_SUPPORTS_PLUGINS */
+
const void *xtensa_load_config (const char *name ATTRIBUTE_UNUSED,
const void *no_plugin_def,
const void *no_name_def ATTRIBUTE_UNUSED)
@@ -75,12 +140,13 @@ const void *xtensa_load_config (const char *name ATTRIBUTE_UNUSED,
if (!init)
{
- const char *path = getenv (CONFIG_ENV_NAME);
+ char *path = get_xtensa_dynconfig_file();
init = 1;
if (!path)
return no_plugin_def;
handle = dlopen (path, RTLD_LAZY);
+ free (path);
if (!handle)
{
_bfd_error_handler (_("%s is defined but could not be loaded: %s"),
@@ -107,7 +173,7 @@ const void *xtensa_load_config (const char *name ATTRIBUTE_UNUSED,
#else
if (!init)
{
- const char *path = getenv (CONFIG_ENV_NAME);
+ const char *path = strcmp(xtensa_dynconfig_file, "") ? xtensa_dynconfig_file : getenv (CONFIG_ENV_NAME);
init = 1;
if (path)
diff --git a/gas/config/tc-xtensa.c b/gas/config/tc-xtensa.c
index e051bb9265b..9debd142fb4 100644
--- a/gas/config/tc-xtensa.c
+++ b/gas/config/tc-xtensa.c
@@ -733,6 +733,8 @@ enum
option_abi_windowed,
option_abi_call0,
+
+ option_dynconfig,
};
const char *md_shortopts = "";
@@ -817,6 +819,8 @@ struct option md_longopts[] =
{ "abi-windowed", no_argument, NULL, option_abi_windowed },
{ "abi-call0", no_argument, NULL, option_abi_call0 },
+ { "dynconfig=", required_argument, NULL, option_dynconfig },
+
{ NULL, no_argument, NULL, 0 }
};
@@ -1053,6 +1057,10 @@ md_parse_option (int c, const char *arg)
elf32xtensa_abi = XTHAL_ABI_CALL0;
return 1;
+ case option_dynconfig:
+ /* Applied in xtensa_init() */
+ return 1;
+
default:
return 0;
}
@@ -1087,7 +1095,9 @@ Xtensa options:\n\
--[no-]separate-prop-tables\n\
[Do not] place Xtensa property records into\n\
individual property sections for each section.\n\
- Default is to generate single property section.\n", stream);
+ Default is to generate single property section.\n\
+ --dynconfig=<file>\n\
+ Use xtensa dynconfig library\n", stream);
}
\f
@@ -5270,6 +5280,10 @@ xg_init_global_config (void)
void
xtensa_init (int argc ATTRIBUTE_UNUSED, char **argv ATTRIBUTE_UNUSED)
{
+ /* This function is called before AS arguments parsed.
+ * So, dynconfig file must be set first. */
+ xtensa_set_dynconfig_from_argv(argc, argv);
+
xg_init_global_config ();
}
diff --git a/include/xtensa-dynconfig.h b/include/xtensa-dynconfig.h
index a0acffea236..a8556498254 100644
--- a/include/xtensa-dynconfig.h
+++ b/include/xtensa-dynconfig.h
@@ -129,6 +129,9 @@ extern const struct xtensa_config_v2 *xtensa_get_config_v2 (void);
extern const struct xtensa_config_v3 *xtensa_get_config_v3 (void);
extern const struct xtensa_config_v4 *xtensa_get_config_v4 (void);
+
+void xtensa_set_dynconfig_from_argv(int argc, char **argv);
+
#ifdef XTENSA_CONFIG_DEFINITION
#ifndef XCHAL_HAVE_MUL32_HIGH
diff --git a/ld/emultempl/xtensaelf.em b/ld/emultempl/xtensaelf.em
index 3508eb7f503..93277f2773d 100644
--- a/ld/emultempl/xtensaelf.em
+++ b/ld/emultempl/xtensaelf.em
@@ -61,6 +61,10 @@ static char *
elf_xtensa_choose_target (int argc ATTRIBUTE_UNUSED,
char **argv ATTRIBUTE_UNUSED)
{
+ /* This function is called before LD arguments parsed.
+ * So, dynconfig file must be set first. */
+ xtensa_set_dynconfig_from_argv(argc, argv);
+
if (XCHAL_HAVE_BE)
return "${BIG_OUTPUT_FORMAT}";
else
@@ -1931,6 +1935,7 @@ PARSE_AND_LIST_LONGOPTS='
{ "no-literal-movement", no_argument, NULL, OPTION_NO_LITERAL_MOVEMENT},
{ "abi-windowed", no_argument, NULL, OPTION_ABI_WINDOWED},
{ "abi-call0", no_argument, NULL, OPTION_ABI_CALL0},
+ { "dynconfig=", required_argument, NULL, OPTION_DYNCONFIG},
'
PARSE_AND_LIST_OPTIONS='
@@ -1941,6 +1946,8 @@ PARSE_AND_LIST_OPTIONS='
--abi-windowed Choose windowed ABI for the output object\n"));
fprintf (file, _("\
--abi-call0 Choose call0 ABI for the output object\n"));
+ fprintf (file, _("\
+ --dynconfig=FILE Choose xtensa dynconfig library\n"));
'
PARSE_AND_LIST_ARGS_CASES='
@@ -1959,6 +1966,9 @@ PARSE_AND_LIST_ARGS_CASES='
case OPTION_ABI_CALL0:
elf32xtensa_abi = XTHAL_ABI_CALL0;
break;
+ case OPTION_DYNCONFIG:
+ /* Applied in elf_xtensa_choose_target() */
+ break;
'
# Replace some of the standard ELF functions with our own versions.
diff --git a/ld/ldlex.h b/ld/ldlex.h
index d575562a357..f43ba4904c1 100644
--- a/ld/ldlex.h
+++ b/ld/ldlex.h
@@ -468,6 +468,7 @@ enum option_values
OPTION_NO_LITERAL_MOVEMENT,
OPTION_ABI_WINDOWED,
OPTION_ABI_CALL0,
+ OPTION_DYNCONFIG,
};
/* The initial parser states. */
--
2.34.1
^ permalink raw reply [flat|nested] 3+ messages in thread
end of thread, other threads:[~2024-04-01 13:01 UTC | newest]
Thread overview: 3+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2023-07-20 14:39 [PATCH] xtensa: add dynconfig option for ld/gas Alexey Lapshin
2023-07-20 14:40 ` Alexey Lapshin
2024-04-01 13:01 ` [PATCH v2] " Alexey Lapshin
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).