This is the mail archive of the binutils@sourceware.org mailing list for the binutils project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: Using S_SET_VOLATILE in md_undefined_symbol crashes as




Hi Nick,

the symbols are defined through the md_undefined_symbol function:

symbolS *
md_undefined_symbol (name)
     char *name;
{
  symbolS *symbolP;

  extract_op (name, op, sizeof (op));
  oper = (struct i51_directop_s *) hash_find (i51_operand, op);
  if (oper == NULL) return 0;
  if ((oper->ref == 'D') || (oper->ref == 'B'))
    {
      symbolP = symbol_new (name, absolute_section, oper->value,
&zero_address_frag);
      S_SET_VOLATILE (symbolP);
      return symbolP;
    }
  else if (oper->ref == 'U')
    {
      if (regbank == 0xFF)
    {
      as_bad (_("missing .using"));
      return 0;
    }
      symbolP = symbol_new (name, absolute_section, regbank +
oper->value, &zero_address_frag);
      S_SET_VOLATILE (symbolP);
      return symbolP;
    }
  else return 0;
}

md_undefined_symbol uses i51_operand that is created in the md_begin
function:

void
md_begin ()
{
  struct i51_opcodes_s *opcode;
  struct i51_directop_s *oper;
  i51_hash = hash_new ();
  i51_operand = hash_new ();

  /* Insert unique names into hash table.  This hash table then provides a
     quick index to the first opcode with a particular name in the opcode
     table.  */
  for (opcode = i51_opcodes; opcode->name; opcode++)
    hash_insert (i51_hash, opcode->name, (char *) opcode);
  /* Insert unique names into hash table.  This hash table then provides a
     quick index to the operand table.  */
  for (oper = i51_directop; oper->op; oper++)
    hash_insert (i51_operand, oper->op, (char *) oper);

  /* We must construct a fake section similar to bfd_com_section
     but with the name .regbank.  */
  scom_section                = *bfd_com_section_ptr;
  scom_section.name           = ".regbank";
  scom_section.output_section = &scom_section;
  scom_section.symbol         = &scom_symbol;
  scom_section.symbol_ptr_ptr = &scom_section.symbol;
  scom_symbol                 = *bfd_com_section_ptr->symbol;
  scom_symbol.name            = ".regbank";
  scom_symbol.section         = &scom_section;
  /* We must construct a fake section similar to bfd_com_section
     but with the name .rbss.  */
  rcom_section                = *bfd_com_section_ptr;
  rcom_section.name           = ".rbss";
  rcom_section.output_section = &rcom_section;
  rcom_section.symbol         = &rcom_symbol;
  rcom_section.symbol_ptr_ptr = &rcom_section.symbol;
  rcom_symbol                 = *bfd_com_section_ptr->symbol;
  rcom_symbol.name            = ".rbss";
  rcom_symbol.section         = &rcom_section;
  /* We must construct a fake section similar to bfd_com_section
     but with the name .bbss.  */
  bcom_section                = *bfd_com_section_ptr;
  bcom_section.name           = ".bbss";
  bcom_section.output_section = &bcom_section;
  bcom_section.symbol         = &bcom_symbol;
  bcom_section.symbol_ptr_ptr = &bcom_section.symbol;
  bcom_symbol                 = *bfd_com_section_ptr->symbol;
  bcom_symbol.name            = ".bbss";
  bcom_symbol.section         = &bcom_section;
  /* We must construct a fake section similar to bfd_com_section
     but with the name .ibss.  */
  icom_section                = *bfd_com_section_ptr;
  icom_section.name           = ".ibss";
  icom_section.output_section = &icom_section;
  icom_section.symbol         = &icom_symbol;
  icom_section.symbol_ptr_ptr = &icom_section.symbol;
  icom_symbol                 = *bfd_com_section_ptr->symbol;
  icom_symbol.name            = ".ibss";
  icom_symbol.section         = &icom_section;
  /* We must construct a fake section similar to bfd_com_section
     but with the name .xbss.  */
  xcom_section                = *bfd_com_section_ptr;
  xcom_section.name           = ".xbss";
  xcom_section.output_section = &xcom_section;
  xcom_section.symbol         = &xcom_symbol;
  xcom_section.symbol_ptr_ptr = &xcom_section.symbol;
  xcom_symbol                 = *bfd_com_section_ptr->symbol;
  xcom_symbol.name            = ".xbss";
  xcom_symbol.section         = &xcom_section;
  /* We must construct a fake section similar to bfd_com_section
     but with the name .ebss.  */
  ecom_section                = *bfd_com_section_ptr;
  ecom_section.name           = ".ebss";
  ecom_section.output_section = &ecom_section;
  ecom_section.symbol         = &ecom_symbol;
  ecom_section.symbol_ptr_ptr = &ecom_section.symbol;
  ecom_symbol                 = *bfd_com_section_ptr->symbol;
  ecom_symbol.name            = ".ebss";
  ecom_symbol.section         = &ecom_section;
  /* We must construct a fake section similar to bfd_com_section
     but with the name .bitbss.  */
  bitcom_section                = *bfd_com_section_ptr;
  bitcom_section.name           = ".bitbss";
  bitcom_section.output_section = &bitcom_section;
  bitcom_section.symbol         = &bitcom_symbol;
  bitcom_section.symbol_ptr_ptr = &bitcom_section.symbol;
  bitcom_symbol                 = *bfd_com_section_ptr->symbol;
  bitcom_symbol.name            = ".bitbss";
  bitcom_symbol.section         = &bitcom_section;
}

i51_directop (i shorted it a bit because its very long) and
i51_directop_s are defined in this way:

struct i51_directop_s
{
  const char *op;
  const char ref;
  const unsigned char value;
};

struct i51_directop_s i51_directop[] =
{
...
{"SP",     'D',0x81},
  {"DPL",    'D',0x82},
  {"DPH",    'D',0x83},
  {"DPL1",   'D',0x84},  // as called by Cypress
  {"DPH1",   'D',0x85},  // as called by Cypress
...
//
  {NULL,     '\0',0}
};

within my source file for example i do:

.equ SP,                    0x81
.equ DPL,                    0x82
.equ DPH,                    0x83
.equ DPL1,                    0x84
.equ DPH1,                    0x85

assign_symbol in read.c uses symbol_clone if the symbol is volatile
should that not replace the symbol? But why it fails?

... greetings HoraK


Am 08.08.2017 um 11:38 schrieb Nick Clifton:
Hi HoraK,

The problem is I have a source file where all registers for the EZ-USB FX2LP are listed and some of them are also defined within the 8051 patch now if as reaches such an symbol it throws an error "symbol ... is already defined"
How are the symbols being defined ?

It may be possible for you to override the way the definition is
parsed and allow the redefinition to occur.

Also - are the register name definitions in the source file necessary ?
One trick used by some ports is to add a prefix to register names, one
that would not occur in ordinary code, such as $ or % or __ .  This
allows user code to create symbols that look like register names, (eg
r1, r2), but which are not the real register names (%r1, %r2) and so
the redefinition error does not occur.

Cheers
   Nick





Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]