/* Configurable Xtensa ISA support.
- Copyright 2003, 2004, 2005 Free Software Foundation, Inc.
+ Copyright (C) 2003-2020 Free Software Foundation, Inc.
This file is part of BFD, the Binary File Descriptor library.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
- the Free Software Foundation; either version 2 of the License, or
+ the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
- Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
+ Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
+ MA 02110-1301, USA. */
-#include "bfd.h"
#include "sysdep.h"
+#include "bfd.h"
#include "libbfd.h"
#include "xtensa-isa.h"
#include "xtensa-isa-internal.h"
/* Inward conversion from byte stream to xtensa_insnbuf. See
xtensa_insnbuf_to_chars for a discussion of why this is complicated
by endianness. */
-
+
void
xtensa_insnbuf_from_chars (xtensa_isa isa,
xtensa_insnbuf insn,
int word_inx = byte_to_word_index (i);
int bit_inx = byte_to_bit_index (i);
- insn[word_inx] |= (*cp & 0xff) << bit_inx;
+ insn[word_inx] |= (unsigned) (*cp & 0xff) << bit_inx;
}
}
xtensa_sysreg_internal *sreg = &isa->sysregs[n];
is_user = sreg->is_user;
- isa->sysreg_table[is_user][sreg->number] = n;
+ if (sreg->number >= 0)
+ isa->sysreg_table[is_user][sreg->number] = n;
}
/* Set up the interface lookup table. */
- isa->interface_lookup_table =
+ isa->interface_lookup_table =
bfd_malloc (isa->num_interfaces * sizeof (xtensa_lookup_entry));
CHECK_ALLOC_FOR_INIT (isa->interface_lookup_table, NULL, errno_p,
error_msg_p);
sizeof (xtensa_lookup_entry), xtensa_isa_name_compare);
/* Set up the funcUnit lookup table. */
- isa->funcUnit_lookup_table =
+ isa->funcUnit_lookup_table =
bfd_malloc (isa->num_funcUnits * sizeof (xtensa_lookup_entry));
CHECK_ALLOC_FOR_INIT (isa->funcUnit_lookup_table, NULL, errno_p,
error_msg_p);
int
-xtensa_isa_num_pipe_stages (xtensa_isa isa)
+xtensa_isa_num_pipe_stages (xtensa_isa isa)
{
xtensa_opcode opcode;
xtensa_funcUnit_use *use;
int num_opcodes, num_uses;
- int i, stage, max_stage = XTENSA_UNDEFINED;
+ int i, stage;
+ static int max_stage = XTENSA_UNDEFINED;
+
+ /* Only compute the value once. */
+ if (max_stage != XTENSA_UNDEFINED)
+ return max_stage + 1;
num_opcodes = xtensa_isa_num_opcodes (isa);
for (opcode = 0; opcode < num_opcodes; opcode++)
if (strcasecmp (fmtname, intisa->formats[fmt].name) == 0)
return fmt;
}
-
+
xtisa_errno = xtensa_isa_bad_format;
sprintf (xtisa_error_msg, "format \"%s\" not recognized", fmtname);
return XTENSA_UNDEFINED;
uint32 test_val, orig_val;
intop = get_operand (intisa, opc, opnd);
- if (!intop) return -1;
+ if (!intop)
+ return -1;
if (!intop->encode)
{
/* This is a default operand for a field. How can we tell if the
value fits in the field? Write the value into the field,
read it back, and then make sure we get the same value. */
-
- xtensa_isa_internal *intisa = (xtensa_isa_internal *) isa;
static xtensa_insnbuf tmpbuf = 0;
int slot_id;
was successfully encoded is to decode it and check if it matches
the original value. */
orig_val = *valp;
- if ((*intop->encode) (valp) ||
- (test_val = *valp, (*intop->decode) (&test_val)) ||
- test_val != orig_val)
+ if ((*intop->encode) (valp)
+ || (test_val = *valp, (*intop->decode) (&test_val))
+ || test_val != orig_val)
{
xtisa_errno = xtensa_isa_bad_value;
sprintf (xtisa_error_msg, "cannot encode operand value 0x%08x", *valp);
/* The expected number of regfiles is small; use a linear search. */
for (n = 0; n < intisa->num_regfiles; n++)
{
- if (!strcmp (intisa->regfiles[n].name, name))
+ if (!filename_cmp (intisa->regfiles[n].name, name))
return n;
}
as their parents. */
if (intisa->regfiles[n].parent != n)
continue;
- if (!strcmp (intisa->regfiles[n].shortname, shortname))
+ if (!filename_cmp (intisa->regfiles[n].shortname, shortname))
return n;
}
}
+int
+xtensa_state_is_shared_or (xtensa_isa isa, xtensa_state st)
+{
+ xtensa_isa_internal *intisa = (xtensa_isa_internal *) isa;
+ CHECK_STATE (intisa, st, XTENSA_UNDEFINED);
+ if ((intisa->states[st].flags & XTENSA_STATE_IS_SHARED_OR) != 0)
+ return 1;
+ return 0;
+}
+
+
\f
/* Sysregs. */