Diff for /qemu/dyngen.c between versions 1.1.1.2 and 1.1.1.3

version 1.1.1.2, 2018/04/24 16:40:55 version 1.1.1.3, 2018/04/24 16:42:57
Line 1196  void get_reloc_expr(char *name, int name Line 1196  void get_reloc_expr(char *name, int name
     } else {      } else {
 #ifdef HOST_SPARC  #ifdef HOST_SPARC
         if (sym_name[0] == '.')          if (sym_name[0] == '.')
             snprintf(name, sizeof(name),              snprintf(name, name_size,
                      "(long)(&__dot_%s)",                       "(long)(&__dot_%s)",
                      sym_name + 1);                       sym_name + 1);
         else          else
Line 1440  void gen_code(const char *name, host_ulo Line 1440  void gen_code(const char *name, host_ulo
     }      }
 #elif defined(HOST_SPARC)  #elif defined(HOST_SPARC)
     {      {
   #define INSN_SAVE       0x9de3a000
   #define INSN_RET        0x81c7e008
   #define INSN_RETL       0x81c3e008
   #define INSN_RESTORE    0x81e80000
   #define INSN_RETURN     0x81cfe008
   #define INSN_NOP        0x01000000
   #define INSN_ADD_SP     0x9c03a000 // add %sp, nn, %sp
   #define INSN_SUB_SP     0x9c23a000 // sub %sp, nn, %sp
   
         uint32_t start_insn, end_insn1, end_insn2;          uint32_t start_insn, end_insn1, end_insn2;
         uint8_t *p;          uint8_t *p;
         p = (void *)(p_end - 8);          p = (void *)(p_end - 8);
Line 1448  void gen_code(const char *name, host_ulo Line 1457  void gen_code(const char *name, host_ulo
         start_insn = get32((uint32_t *)(p_start + 0x0));          start_insn = get32((uint32_t *)(p_start + 0x0));
         end_insn1 = get32((uint32_t *)(p + 0x0));          end_insn1 = get32((uint32_t *)(p + 0x0));
         end_insn2 = get32((uint32_t *)(p + 0x4));          end_insn2 = get32((uint32_t *)(p + 0x4));
         if ((start_insn & ~0x1fff) == 0x9de3a000) {          if (((start_insn & ~0x1fff) == INSN_SAVE) ||
               (start_insn & ~0x1fff) == INSN_ADD_SP) {
             p_start += 0x4;              p_start += 0x4;
             start_offset += 0x4;              start_offset += 0x4;
             if ((int)(start_insn | ~0x1fff) < -128)              if (end_insn1 == INSN_RET && end_insn2 == INSN_RESTORE)
                 error("Found bogus save at the start of %s", name);                  /* SPARC v7: ret; restore; */ ;
             if (end_insn1 != 0x81c7e008 || end_insn2 != 0x81e80000)              else if (end_insn1 == INSN_RETURN && end_insn2 == INSN_NOP)
                   /* SPARC v9: return; nop; */ ;
               else if (end_insn1 == INSN_RETL && (end_insn2 & ~0x1fff) == INSN_SUB_SP)
                   /* SPARC v7: retl; sub %sp, nn, %sp; */ ;
               else
   
                 error("ret; restore; not found at end of %s", name);                  error("ret; restore; not found at end of %s", name);
           } else if (end_insn1 == INSN_RETL && end_insn2 == INSN_NOP) {
               ;
         } else {          } else {
             error("No save at the beginning of %s", name);              error("No save at the beginning of %s", name);
         }          }
Line 1462  void gen_code(const char *name, host_ulo Line 1479  void gen_code(const char *name, host_ulo
         /* Skip a preceeding nop, if present.  */          /* Skip a preceeding nop, if present.  */
         if (p > p_start) {          if (p > p_start) {
             skip_insn = get32((uint32_t *)(p - 0x4));              skip_insn = get32((uint32_t *)(p - 0x4));
             if (skip_insn == 0x01000000)              if (skip_insn == INSN_NOP)
                 p -= 4;                  p -= 4;
         }          }
 #endif  #endif
Line 1470  void gen_code(const char *name, host_ulo Line 1487  void gen_code(const char *name, host_ulo
     }      }
 #elif defined(HOST_SPARC64)  #elif defined(HOST_SPARC64)
     {      {
   #define INSN_SAVE       0x9de3a000
   #define INSN_RET        0x81c7e008
   #define INSN_RETL       0x81c3e008
   #define INSN_RESTORE    0x81e80000
   #define INSN_RETURN     0x81cfe008
   #define INSN_NOP        0x01000000
   #define INSN_ADD_SP     0x9c03a000 // add %sp, nn, %sp
   #define INSN_SUB_SP     0x9c23a000 // sub %sp, nn, %sp
   
         uint32_t start_insn, end_insn1, end_insn2, skip_insn;          uint32_t start_insn, end_insn1, end_insn2, skip_insn;
         uint8_t *p;          uint8_t *p;
         p = (void *)(p_end - 8);          p = (void *)(p_end - 8);
   #if 0
           /* XXX: check why it occurs */
         if (p <= p_start)          if (p <= p_start)
             error("empty code for %s", name);              error("empty code for %s", name);
   #endif
         start_insn = get32((uint32_t *)(p_start + 0x0));          start_insn = get32((uint32_t *)(p_start + 0x0));
         end_insn1 = get32((uint32_t *)(p + 0x0));          end_insn1 = get32((uint32_t *)(p + 0x0));
         end_insn2 = get32((uint32_t *)(p + 0x4));          end_insn2 = get32((uint32_t *)(p + 0x4));
         if ((start_insn & ~0x1fff) == 0x9de3a000) {          if (((start_insn & ~0x1fff) == INSN_SAVE) ||
               (start_insn & ~0x1fff) == INSN_ADD_SP) {
             p_start += 0x4;              p_start += 0x4;
             start_offset += 0x4;              start_offset += 0x4;
             if ((int)(start_insn | ~0x1fff) < -256)              if (end_insn1 == INSN_RET && end_insn2 == INSN_RESTORE)
                 error("Found bogus save at the start of %s", name);                  /* SPARC v7: ret; restore; */ ;
             if (end_insn1 != 0x81c7e008 || end_insn2 != 0x81e80000)              else if (end_insn1 == INSN_RETURN && end_insn2 == INSN_NOP)
                   /* SPARC v9: return; nop; */ ;
               else if (end_insn1 == INSN_RETL && (end_insn2 & ~0x1fff) == INSN_SUB_SP)
                   /* SPARC v7: retl; sub %sp, nn, %sp; */ ;
               else
   
                 error("ret; restore; not found at end of %s", name);                  error("ret; restore; not found at end of %s", name);
           } else if (end_insn1 == INSN_RETL && end_insn2 == INSN_NOP) {
               ;
         } else {          } else {
             error("No save at the beginning of %s", name);              error("No save at the beginning of %s", name);
         }          }
Line 2151  void gen_code(const char *name, host_ulo Line 2188  void gen_code(const char *name, host_ulo
                                     reloc_offset, reloc_offset, name, addend,                                      reloc_offset, reloc_offset, name, addend,
                                     reloc_offset);                                      reloc_offset);
                             break;                              break;
                           case R_SPARC_WDISP22:
                               fprintf(outfile,
                                       "    *(uint32_t *)(gen_code_ptr + %d) = "
                                       "((*(uint32_t *)(gen_code_ptr + %d)) "
                                       " & ~0x3fffff) "
                                       " | ((((%s + %d) - (long)(gen_code_ptr + %d))>>2) "
                                       "    & 0x3fffff);\n",
                                       rel->r_offset - start_offset,
                                       rel->r_offset - start_offset,
                                       name, addend,
                                       rel->r_offset - start_offset);
                               break;
                         default:                          default:
                             error("unsupported sparc relocation (%d)", type);                              error("unsupported sparc relocation (%d)", type);
                         }                          }
Line 2168  void gen_code(const char *name, host_ulo Line 2217  void gen_code(const char *name, host_ulo
                         rel->r_offset < start_offset + copy_size) {                          rel->r_offset < start_offset + copy_size) {
                         sym_name = strtab + symtab[ELF64_R_SYM(rel->r_info)].st_name;                          sym_name = strtab + symtab[ELF64_R_SYM(rel->r_info)].st_name;
                         get_reloc_expr(name, sizeof(name), sym_name);                          get_reloc_expr(name, sizeof(name), sym_name);
                         type = ELF64_R_TYPE(rel->r_info);                          type = ELF32_R_TYPE(rel->r_info);
                         addend = rel->r_addend;                          addend = rel->r_addend;
                         reloc_offset = rel->r_offset - start_offset;                          reloc_offset = rel->r_offset - start_offset;
                         switch(type) {                          switch(type) {
Line 2192  void gen_code(const char *name, host_ulo Line 2241  void gen_code(const char *name, host_ulo
                                     " | ((%s + %d) & 0x3ff);\n",                                      " | ((%s + %d) & 0x3ff);\n",
                                     reloc_offset, reloc_offset, name, addend);                                      reloc_offset, reloc_offset, name, addend);
                             break;                              break;
                           case R_SPARC_OLO10:
                               addend += ELF64_R_TYPE_DATA (rel->r_info);
                               fprintf(outfile,
                                       "    *(uint32_t *)(gen_code_ptr + %d) = "
                                       "((*(uint32_t *)(gen_code_ptr + %d)) "
                                       " & ~0x3ff) "
                                       " | ((%s + %d) & 0x3ff);\n",
                                       reloc_offset, reloc_offset, name, addend);
                               break;
                         case R_SPARC_WDISP30:                          case R_SPARC_WDISP30:
                             fprintf(outfile,                              fprintf(outfile,
                                     "    *(uint32_t *)(gen_code_ptr + %d) = "                                      "    *(uint32_t *)(gen_code_ptr + %d) = "
Line 2202  void gen_code(const char *name, host_ulo Line 2260  void gen_code(const char *name, host_ulo
                                     reloc_offset, reloc_offset, name, addend,                                      reloc_offset, reloc_offset, name, addend,
                                     reloc_offset);                                      reloc_offset);
                             break;                              break;
                           case R_SPARC_WDISP22:
                               fprintf(outfile,
                                       "    *(uint32_t *)(gen_code_ptr + %d) = "
                                       "((*(uint32_t *)(gen_code_ptr + %d)) "
                                       " & ~0x3fffff) "
                                       " | ((((%s + %d) - (long)(gen_code_ptr + %d))>>2) "
                                       "    & 0x3fffff);\n",
                                       reloc_offset, reloc_offset, name, addend,
                                       reloc_offset);
                               break;
                         default:                          default:
                             error("unsupported sparc64 relocation (%d)", type);                              error("unsupported sparc64 relocation (%d) for symbol %s", type, name);
                         }                          }
                     }                      }
                 }                  }

Removed from v.1.1.1.2  
changed lines
  Added in v.1.1.1.3


unix.superglobalmegacorp.com