gdb: add target_ops::supports_displaced_step
[deliverable/binutils-gdb.git] / bfd / vms-alpha.c
index 594363b32afe7ad590515f9610851e5bf68a0402..e31a9e4ca10bca344dab67ea208b0784ffb85458 100644 (file)
@@ -1611,26 +1611,35 @@ dst_retrieve_location (bfd *abfd, bfd_vma *loc)
 static bfd_boolean
 image_write (bfd *abfd, unsigned char *ptr, unsigned int size)
 {
+  asection *sec = PRIV (image_section);
+  size_t off = PRIV (image_offset);
+
+  /* Check bounds.  */
+  if (off > sec->size
+      || size > sec->size - off)
+    {
+      bfd_set_error (bfd_error_bad_value);
+      return FALSE;
+    }
+
 #if VMS_DEBUG
   _bfd_vms_debug (8, "image_write from (%p, %d) to (%ld)\n", ptr, size,
-                 (long)PRIV (image_offset));
+                 (long) off));
 #endif
 
   if (PRIV (image_section)->contents != NULL)
+    memcpy (sec->contents + off, ptr, size);
+  else
     {
-      asection *sec = PRIV (image_section);
-      size_t off = PRIV (image_offset);
-
-      /* Check bounds.  */
-      if (off > sec->size
-         || size > sec->size - off)
-       {
-         bfd_set_error (bfd_error_bad_value);
-         return FALSE;
-       }
-
-      memcpy (sec->contents + off, ptr, size);
+      unsigned int i;
+      for (i = 0; i < size; i++)
+       if (ptr[i] != 0)
+         {
+           bfd_set_error (bfd_error_bad_value);
+           return FALSE;
+         }
     }
+
 #if VMS_DEBUG
   _bfd_hexdump (9, ptr, size, 0);
 #endif
@@ -1916,11 +1925,12 @@ _bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info)
          return FALSE;
        }
       ptr += 4;
+      cmd_length -= 4;
 
 #if VMS_DEBUG
       _bfd_vms_debug (4, "etir: %s(%d)\n",
                      _bfd_vms_etir_name (cmd), cmd);
-      _bfd_hexdump (8, ptr, cmd_length - 4, 0);
+      _bfd_hexdump (8, ptr, cmd_length, 0);
 #endif
 
       switch (cmd)
@@ -1930,7 +1940,7 @@ _bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info)
 
             stack 32 bit value of symbol (high bits set to 0).  */
        case ETIR__C_STA_GBL:
-         _bfd_vms_get_value (abfd, ptr, maxptr, info, &op1, &h);
+         _bfd_vms_get_value (abfd, ptr, ptr + cmd_length, info, &op1, &h);
          if (!_bfd_vms_push (abfd, op1, alpha_vms_sym_to_ctxt (h)))
            return FALSE;
          break;
@@ -1940,7 +1950,7 @@ _bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info)
 
             stack 32 bit value, sign extend to 64 bit.  */
        case ETIR__C_STA_LW:
-         if (ptr + 4 > maxptr)
+         if (cmd_length < 4)
            goto corrupt_etir;
          if (!_bfd_vms_push (abfd, bfd_getl32 (ptr), RELC_NONE))
            return FALSE;
@@ -1951,7 +1961,7 @@ _bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info)
 
             stack 64 bit value of symbol.  */
        case ETIR__C_STA_QW:
-         if (ptr + 8 > maxptr)
+         if (cmd_length < 8)
            goto corrupt_etir;
          if (!_bfd_vms_push (abfd, bfd_getl64 (ptr), RELC_NONE))
            return FALSE;
@@ -1967,7 +1977,7 @@ _bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info)
          {
            int psect;
 
-           if (ptr + 12 > maxptr)
+           if (cmd_length < 12)
              goto corrupt_etir;
            psect = bfd_getl32 (ptr);
            if ((unsigned int) psect >= PRIV (section_count))
@@ -1998,7 +2008,8 @@ _bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info)
            return FALSE;
          if (rel1 != RELC_NONE)
            goto bad_context;
-         image_write_b (abfd, (unsigned int) op1 & 0xff);
+         if (!image_write_b (abfd, (unsigned int) op1 & 0xff))
+           return FALSE;
          break;
 
          /* Store word: pop stack, write word
@@ -2008,7 +2019,8 @@ _bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info)
            return FALSE;
          if (rel1 != RELC_NONE)
            goto bad_context;
-         image_write_w (abfd, (unsigned int) op1 & 0xffff);
+         if (!image_write_w (abfd, (unsigned int) op1 & 0xffff))
+           return FALSE;
          break;
 
          /* Store longword: pop stack, write longword
@@ -2034,7 +2046,8 @@ _bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info)
              if (!alpha_vms_add_lw_reloc (info))
                return FALSE;
            }
-         image_write_l (abfd, op1);
+         if (!image_write_l (abfd, op1))
+           return FALSE;
          break;
 
          /* Store quadword: pop stack, write quadword
@@ -2056,7 +2069,8 @@ _bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info)
              if (!alpha_vms_add_qw_reloc (info))
                return FALSE;
            }
-         image_write_q (abfd, op1);
+         if (!image_write_q (abfd, op1))
+           return FALSE;
          break;
 
          /* Store immediate repeated: pop stack for repeat count
@@ -2066,22 +2080,28 @@ _bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info)
          {
            int size;
 
-           if (ptr + 4 > maxptr)
+           if (cmd_length < 4)
              goto corrupt_etir;
            size = bfd_getl32 (ptr);
+           if (size > cmd_length - 4)
+             goto corrupt_etir;
            if (!_bfd_vms_pop (abfd, &op1, &rel1))
              return FALSE;
            if (rel1 != RELC_NONE)
              goto bad_context;
+           if (size == 0)
+             break;
+           op1 &= 0xffffffff;
            while (op1-- > 0)
-             image_write (abfd, ptr + 4, size);
+             if (!image_write (abfd, ptr + 4, size))
+               return FALSE;
          }
          break;
 
          /* Store global: write symbol value
             arg: cs    global symbol name.  */
        case ETIR__C_STO_GBL:
-         _bfd_vms_get_value (abfd, ptr, maxptr, info, &op1, &h);
+         _bfd_vms_get_value (abfd, ptr, ptr + cmd_length, info, &op1, &h);
          if (h && h->sym)
            {
              if (h->sym->typ == EGSD__C_SYMG)
@@ -2099,13 +2119,14 @@ _bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info)
                    return FALSE;
                }
            }
-         image_write_q (abfd, op1);
+         if (!image_write_q (abfd, op1))
+           return FALSE;
          break;
 
          /* Store code address: write address of entry point
             arg: cs    global symbol name (procedure).  */
        case ETIR__C_STO_CA:
-         _bfd_vms_get_value (abfd, ptr, maxptr, info, &op1, &h);
+         _bfd_vms_get_value (abfd, ptr, ptr + cmd_length, info, &op1, &h);
          if (h && h->sym)
            {
              if (h->sym->flags & EGSY__V_NORM)
@@ -2131,7 +2152,8 @@ _bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info)
                  abort ();
                }
            }
-         image_write_q (abfd, op1);
+         if (!image_write_q (abfd, op1))
+           return FALSE;
          break;
 
          /* Store offset to psect: pop stack, add low 32 bits to base of psect
@@ -2145,7 +2167,8 @@ _bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info)
 
          op1 = alpha_vms_fix_sec_rel (abfd, info, rel1, op1);
          rel1 = RELC_REL;
-         image_write_q (abfd, op1);
+         if (!image_write_q (abfd, op1))
+           return FALSE;
          break;
 
          /* Store immediate
@@ -2155,10 +2178,11 @@ _bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info)
          {
            unsigned int size;
 
-           if (ptr + 4 > maxptr)
+           if (cmd_length < 4)
              goto corrupt_etir;
            size = bfd_getl32 (ptr);
-           image_write (abfd, ptr + 4, size);
+           if (!image_write (abfd, ptr + 4, size))
+             return FALSE;
          }
          break;
 
@@ -2169,11 +2193,12 @@ _bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info)
             store global longword: store 32bit value of symbol
             arg: cs    symbol name.  */
        case ETIR__C_STO_GBL_LW:
-         _bfd_vms_get_value (abfd, ptr, maxptr, info, &op1, &h);
+         _bfd_vms_get_value (abfd, ptr, ptr + cmd_length, info, &op1, &h);
 #if 0
          abort ();
 #endif
-         image_write_l (abfd, op1);
+         if (!image_write_l (abfd, op1))
+           return FALSE;
          break;
 
        case ETIR__C_STO_RB:
@@ -2222,7 +2247,9 @@ _bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info)
             da signature.  */
 
        case ETIR__C_STC_LP_PSB:
-         _bfd_vms_get_value (abfd, ptr + 4, maxptr, info, &op1, &h);
+         if (cmd_length < 4)
+           goto corrupt_etir;
+         _bfd_vms_get_value (abfd, ptr + 4, ptr + cmd_length, info, &op1, &h);
          if (h && h->sym)
            {
              if (h->sym->typ == EGSD__C_SYMG)
@@ -2246,8 +2273,9 @@ _bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info)
              op1 = 0;
              op2 = 0;
            }
-         image_write_q (abfd, op1);
-         image_write_q (abfd, op2);
+         if (!image_write_q (abfd, op1)
+             || !image_write_q (abfd, op2))
+           return FALSE;
          break;
 
          /* 205 Store-conditional NOP at address of global
@@ -2320,7 +2348,7 @@ _bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info)
          /* Augment relocation base: increment image location counter by offset
             arg: lw    offset value.  */
        case ETIR__C_CTL_AUGRB:
-         if (ptr + 4 > maxptr)
+         if (cmd_length < 4)
            goto corrupt_etir;
          op1 = bfd_getl32 (ptr);
          image_inc_ptr (abfd, op1);
@@ -2418,8 +2446,11 @@ _bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info)
            return FALSE;
          if (rel1 != RELC_NONE || rel2 != RELC_NONE)
            goto bad_context;
-         if (op2 == 0)
+         if (op1 == 0)
            {
+             /* Divide by zero is supposed to give a result of zero,
+                and a non-fatal warning message.  */
+             _bfd_error_handler (_("%s divide by zero"), "ETIR__C_OPR_DIV");
              if (!_bfd_vms_push (abfd, 0, RELC_NONE))
                return FALSE;
            }
@@ -2531,7 +2562,7 @@ _bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info)
          break;
        }
 
-      ptr += cmd_length - 4;
+      ptr += cmd_length;
     }
 
   return TRUE;
This page took 0.031731 seconds and 4 git commands to generate.