2009-11-16 Kai Tietz <kai.tietz@onevision.com>

* targets.c (bfd_get_target_info): New function.
        (_bfd_find_arch_match): New function.
        * bfd-in2.h: Regenerated.
This commit is contained in:
Kai Tietz 2009-11-16 11:11:11 +00:00
parent d204b6e935
commit 5fbe97211b
3 changed files with 126 additions and 0 deletions

View File

@ -1,3 +1,9 @@
2009-11-16 Kai Tietz <kai.tietz@onevision.com>
* targets.c (bfd_get_target_info): New function.
(_bfd_find_arch_match): New function.
* bfd-in2.h: Regenerated.
2009-11-12 Nick Clifton <nickc@redhat.com>
* po/ru.po: Updates Russian translation.

View File

@ -5692,6 +5692,11 @@ bfd_boolean bfd_set_default_target (const char *name);
const bfd_target *bfd_find_target (const char *target_name, bfd *abfd);
const bfd_target *bfd_get_target_info (const char *target_name,
bfd *abfd,
bfd_boolean *is_bigendian,
int *underscoring,
const char **def_target_arch);
const char ** bfd_target_list (void);
const bfd_target *bfd_search_for_target

View File

@ -1428,6 +1428,121 @@ bfd_find_target (const char *target_name, bfd *abfd)
return target;
}
/* Helper function for bfd_get_target_info to determine the target's
architecture. This method handles bfd internal target names as
tuples and triplets. */
static bfd_boolean
_bfd_find_arch_match (const char *tname, const char **arch,
const char **def_target_arch)
{
if (!arch)
return FALSE;
while (*arch != NULL)
{
const char *in_a = strstr (*arch, tname);
char end_ch = (in_a ? in_a[strlen (tname)] : 0);
if (in_a && (in_a == *arch || in_a[-1] == ':')
&& end_ch == 0)
{
*def_target_arch = *arch;
return TRUE;
}
arch++;
}
return FALSE;
}
/*
FUNCTION
bfd_get_target_info
SYNOPSIS
const bfd_target *bfd_get_target_info (const char *target_name,
bfd *abfd,
bfd_boolean *is_bigendian,
int *underscoring,
const char **def_target_arch);
DESCRIPTION
Return a pointer to the transfer vector for the object target
named @var{target_name}. If @var{target_name} is <<NULL>>,
choose the one in the environment variable <<GNUTARGET>>; if
that is null or not defined, then choose the first entry in the
target list. Passing in the string "default" or setting the
environment variable to "default" will cause the first entry in
the target list to be returned, and "target_defaulted" will be
set in the BFD if @var{abfd} isn't <<NULL>>. This causes
<<bfd_check_format>> to loop over all the targets to find the
one that matches the file being read.
If @var{is_bigendian} is not <<NULL>>, then set this value to target's
endian mode. True for big-endian, FALSE for little-endian or for
invalid target.
If @var{underscoring} is not <<NULL>>, then set this value to target's
underscoring mode. Zero for none-underscoring, -1 for invalid target,
else the value of target vector's symbol underscoring.
If @var{def_target_arch} is not <<NULL>>, then set it to the architecture
string specified by the target_name.
*/
const bfd_target *
bfd_get_target_info (const char *target_name, bfd *abfd,
bfd_boolean *is_bigendian,
int *underscoring, const char **def_target_arch)
{
const bfd_target *target_vec;
if (is_bigendian)
*is_bigendian = FALSE;
if (underscoring)
*underscoring = -1;
if (def_target_arch)
*def_target_arch = NULL;
target_vec = bfd_find_target (target_name, abfd);
if (! target_vec)
return NULL;
if (is_bigendian)
*is_bigendian = ((target_vec->byteorder == BFD_ENDIAN_BIG) ? TRUE
: FALSE);
if (underscoring)
*underscoring = ((int) target_vec->symbol_leading_char) & 0xff;
if (def_target_arch)
{
const char *tname = target_vec->name;
const char **arches = bfd_arch_list ();
if (arches && tname)
{
char *hyp = strchr (tname, '-');
if (hyp != NULL)
{
tname = ++hyp;
/* Make sure we detect architecture names
for triplets like "pe-arm-wince-little". */
if (!_bfd_find_arch_match (tname, arches, def_target_arch))
{
char *new_tname = (char *) alloca (strlen (hyp) + 1);
strcpy (new_tname, hyp);
while ((hyp = strrchr (new_tname, '-')) != NULL)
{
*hyp = 0;
if (_bfd_find_arch_match (new_tname, arches,
def_target_arch))
break;
}
}
}
else
_bfd_find_arch_match (tname, arches, def_target_arch);
}
if (arches)
free (arches);
}
return target_vec;
}
/*
FUNCTION
bfd_target_list