Home | History | Annotate | Download | only in m_gdbserver
      1 /* Low level interface to valgrind, for the remote server for GDB integrated
      2    in valgrind.
      3    Copyright (C) 2011
      4    Free Software Foundation, Inc.
      5 
      6    This file is part of VALGRIND.
      7    It has been inspired from a file from gdbserver in gdb 6.6.
      8 
      9    This program is free software; you can redistribute it and/or modify
     10    it under the terms of the GNU General Public License as published by
     11    the Free Software Foundation; either version 2 of the License, or
     12    (at your option) any later version.
     13 
     14    This program is distributed in the hope that it will be useful,
     15    but WITHOUT ANY WARRANTY; without even the implied warranty of
     16    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
     17    GNU General Public License for more details.
     18 
     19    You should have received a copy of the GNU General Public License
     20    along with this program; if not, write to the Free Software
     21    Foundation, Inc., 51 Franklin Street, Fifth Floor,
     22    Boston, MA 02110-1301, USA.  */
     23 
     24 #include "server.h"
     25 #include "target.h"
     26 #include "regdef.h"
     27 #include "regcache.h"
     28 
     29 #include "pub_core_aspacemgr.h"
     30 #include "pub_core_machine.h"
     31 #include "pub_core_debuginfo.h"
     32 #include "pub_core_threadstate.h"
     33 #include "pub_core_transtab.h"
     34 #include "pub_core_gdbserver.h"
     35 
     36 #include "valgrind_low.h"
     37 
     38 #include "libvex_guest_mips64.h"
     39 
     40 static struct reg regs[] = {
     41    { "r0", 0, 64 },
     42    { "r1", 64, 64 },
     43    { "r2", 128, 64 },
     44    { "r3", 192, 64 },
     45    { "r4", 256, 64 },
     46    { "r5", 320, 64 },
     47    { "r6", 384, 64 },
     48    { "r7", 448, 64 },
     49    { "r8", 512, 64 },
     50    { "r9", 576, 64 },
     51    { "r10", 640, 64 },
     52    { "r11", 704, 64 },
     53    { "r12", 768, 64 },
     54    { "r13", 832, 64 },
     55    { "r14", 896, 64 },
     56    { "r15", 960, 64 },
     57    { "r16", 1024, 64 },
     58    { "r17", 1088, 64 },
     59    { "r18", 1152, 64 },
     60    { "r19", 1216, 64 },
     61    { "r20", 1280, 64 },
     62    { "r21", 1344, 64 },
     63    { "r22", 1408, 64 },
     64    { "r23", 1472, 64 },
     65    { "r24", 1536, 64 },
     66    { "r25", 1600, 64 },
     67    { "r26", 1664, 64 },
     68    { "r27", 1728, 64 },
     69    { "r28", 1792, 64 },
     70    { "r29", 1856, 64 },
     71    { "r30", 1920, 64 },
     72    { "r31", 1984, 64 },
     73    { "status", 2048, 64 },
     74    { "lo", 2112, 64 },
     75    { "hi", 2176, 64 },
     76    { "badvaddr", 2240, 64 },
     77    { "cause", 2304, 64 },
     78    { "pc", 2368, 64 },
     79    { "f0", 2432, 64 },
     80    { "f1", 2496, 64 },
     81    { "f2", 2560, 64 },
     82    { "f3", 2624, 64 },
     83    { "f4", 2688, 64 },
     84    { "f5", 2752, 64 },
     85    { "f6", 2816, 64 },
     86    { "f7", 2880, 64 },
     87    { "f8", 2944, 64 },
     88    { "f9", 3008, 64 },
     89    { "f10", 3072, 64 },
     90    { "f11", 3136, 64 },
     91    { "f12", 3200, 64 },
     92    { "f13", 3264, 64 },
     93    { "f14", 3328, 64 },
     94    { "f15", 3392, 64 },
     95    { "f16", 3456, 64 },
     96    { "f17", 3520, 64 },
     97    { "f18", 3584, 64 },
     98    { "f19", 3648, 64 },
     99    { "f20", 3712, 64 },
    100    { "f21", 3776, 64 },
    101    { "f22", 3840, 64 },
    102    { "f23", 3904, 64 },
    103    { "f24", 3968, 64 },
    104    { "f25", 4032, 64 },
    105    { "f26", 4096, 64 },
    106    { "f27", 4160, 64 },
    107    { "f28", 4224, 64 },
    108    { "f29", 4288, 64 },
    109    { "f30", 4352, 64 },
    110    { "f31", 4416, 64 },
    111    { "fcsr", 4480, 64 },
    112    { "fir", 4544, 64 },
    113    { "restart", 4608, 64 }
    114 };
    115 
    116 
    117 #define num_regs (sizeof (regs) / sizeof (regs[0]))
    118 
    119 static const char *expedite_regs[] = { "r29", "pc", 0 };
    120 
    121 static
    122 CORE_ADDR get_pc (void)
    123 {
    124    unsigned long pc;
    125 
    126    collect_register_by_name ("pc", &pc);
    127 
    128    dlog(1, "stop pc is %p\n", (void *) pc);
    129    return pc;
    130 }
    131 
    132 static
    133 void set_pc (CORE_ADDR newpc)
    134 {
    135    Bool mod;
    136    supply_register_by_name ("pc", &newpc, &mod);
    137    if (mod)
    138       dlog(1, "set pc to %p\n", C2v (newpc));
    139    else
    140       dlog(1, "set pc not changed %p\n", C2v (newpc));
    141 }
    142 
    143 /* These are the fields of 32 bit mips instructions. */
    144 #define itype_op(x) (x >> 26)
    145 #define itype_rs(x) ((x >> 21) & 0x1f)
    146 #define itype_rt(x) ((x >> 16) & 0x1f)
    147 #define rtype_funct(x) (x & 0x3f)
    148 
    149 /* Do a endian load of a 32-bit word, regardless of the
    150    endianness of the underlying host. */
    151 static inline UInt getUInt(UChar * p)
    152 {
    153    UInt w = 0;
    154 #if defined (_MIPSEL)
    155    w = (w << 8) | p[3];
    156    w = (w << 8) | p[2];
    157    w = (w << 8) | p[1];
    158    w = (w << 8) | p[0];
    159 #elif defined (_MIPSEB)
    160    w = (w << 8) | p[0];
    161    w = (w << 8) | p[1];
    162    w = (w << 8) | p[2];
    163    w = (w << 8) | p[3];
    164 #endif
    165    return w;
    166 }
    167 
    168 /* Return non-zero if the ADDR instruction has a branch delay slot
    169    (i.e. it is a jump or branch instruction). */
    170 static UInt
    171 mips_instruction_has_delay_slot (Addr addr)
    172 {
    173    UInt op, rs, rt;
    174    UInt inst = getUInt((UChar *)addr);
    175 
    176    op = itype_op (inst);
    177    if ((inst & 0xe0000000) != 0) {
    178       rs = itype_rs (inst);
    179       rt = itype_rt (inst);
    180       return (op >> 2 == 5        /* BEQL, BNEL, BLEZL, BGTZL: bits 0101xx  */
    181               || op == 29         /* JALX: bits 011101  */
    182               || (op == 17
    183                   && (rs == 8     /* BC1F, BC1FL, BC1T, BC1TL: 010001 01000  */
    184                       || (rs == 9 && (rt & 0x2) == 0)
    185                                   /* BC1ANY2F, BC1ANY2T: bits 010001 01001  */
    186                       || (rs == 10 && (rt & 0x2) == 0))));
    187                                   /* BC1ANY4F, BC1ANY4T: bits 010001 01010  */
    188    } else
    189       switch (op & 0x07) {        /* extract bits 28,27,26  */
    190          case 0:                  /* SPECIAL  */
    191             op = rtype_funct (inst);
    192          return (op == 8          /* JR  */
    193                  || op == 9);     /* JALR  */
    194          break;                   /* end SPECIAL  */
    195          case 1:                  /* REGIMM  */
    196             rs = itype_rs (inst);
    197             rt = itype_rt (inst); /* branch condition  */
    198             return ((rt & 0xc) == 0
    199                                   /* BLTZ, BLTZL, BGEZ, BGEZL: bits 000xx  */
    200                                   /* BLTZAL, BLTZALL, BGEZAL, BGEZALL: 100xx  */
    201                     || ((rt & 0x1e) == 0x1c && rs == 0));
    202                                   /* BPOSGE32, BPOSGE64: bits 1110x  */
    203             break;                /* end REGIMM  */
    204          default:                 /* J, JAL, BEQ, BNE, BLEZ, BGTZ  */
    205             return 1;
    206             break;
    207    }
    208 }
    209 
    210 /* Move the breakpoint at BPADDR out of any branch delay slot by shifting
    211    it backwards if necessary.  Return the address of the new location.  */
    212 static Addr mips_adjust_breakpoint_address (Addr pc)
    213 {
    214    Addr prev_addr;
    215    Addr boundary;
    216    Addr func_addr;
    217    Addr bpaddr = pc;
    218    Addr mask = (Addr)0xffffffffffffffffULL;
    219    int segsize;
    220    PtrdiffT offset;
    221 
    222    /* Calculate the starting address of the MIPS memory segment pc is in. */
    223    if (bpaddr & 0x80000000)  /* kernel segment */
    224       segsize = 29;
    225    else
    226       segsize = 31;          /* user segment */
    227    mask <<= segsize;
    228    boundary = pc & mask;
    229 
    230    /* Make sure we don't scan back before the beginning of the current
    231       function, since we may fetch constant data or insns that look like
    232       a jump. */
    233    if (VG_(get_inst_offset_in_function) (bpaddr, &offset)) {
    234       func_addr = bpaddr - offset;
    235       if (func_addr > boundary && func_addr <= bpaddr)
    236          boundary = func_addr;
    237    }
    238 
    239    if (bpaddr == boundary)
    240       return bpaddr;
    241    /* If the previous instruction has a branch delay slot, we have
    242       to move the breakpoint to the branch instruction. */
    243    prev_addr = bpaddr - 4;
    244    if (mips_instruction_has_delay_slot (prev_addr))
    245       bpaddr = prev_addr;
    246 
    247    return bpaddr;
    248 }
    249 
    250 /* store registers in the guest state (gdbserver_to_valgrind)
    251    or fetch register from the guest state (valgrind_to_gdbserver). */
    252 static
    253 void transfer_register (ThreadId tid, int abs_regno, void * buf,
    254                         transfer_direction dir, int size, Bool *mod)
    255 {
    256    ThreadState* tst = VG_(get_ThreadState)(tid);
    257    int set = abs_regno / num_regs;
    258    int regno = abs_regno % num_regs;
    259    *mod = False;
    260 
    261    VexGuestMIPS64State* mips1 = (VexGuestMIPS64State*) get_arch (set, tst);
    262 
    263    switch (regno) {
    264    case 0:  VG_(transfer) (&mips1->guest_r0,  buf, dir, size, mod); break;
    265    case 1:  VG_(transfer) (&mips1->guest_r1,  buf, dir, size, mod); break;
    266    case 2:  VG_(transfer) (&mips1->guest_r2,  buf, dir, size, mod); break;
    267    case 3:  VG_(transfer) (&mips1->guest_r3,  buf, dir, size, mod); break;
    268    case 4:  VG_(transfer) (&mips1->guest_r4,  buf, dir, size, mod); break;
    269    case 5:  VG_(transfer) (&mips1->guest_r5,  buf, dir, size, mod); break;
    270    case 6:  VG_(transfer) (&mips1->guest_r6,  buf, dir, size, mod); break;
    271    case 7:  VG_(transfer) (&mips1->guest_r7,  buf, dir, size, mod); break;
    272    case 8:  VG_(transfer) (&mips1->guest_r8,  buf, dir, size, mod); break;
    273    case 9:  VG_(transfer) (&mips1->guest_r9,  buf, dir, size, mod); break;
    274    case 10: VG_(transfer) (&mips1->guest_r10,  buf, dir, size, mod); break;
    275    case 11: VG_(transfer) (&mips1->guest_r11,  buf, dir, size, mod); break;
    276    case 12: VG_(transfer) (&mips1->guest_r12, buf, dir, size, mod); break;
    277    case 13: VG_(transfer) (&mips1->guest_r13, buf, dir, size, mod); break;
    278    case 14: VG_(transfer) (&mips1->guest_r14, buf, dir, size, mod); break;
    279    case 15: VG_(transfer) (&mips1->guest_r15, buf, dir, size, mod); break;
    280    case 16: VG_(transfer) (&mips1->guest_r16, buf, dir, size, mod); break;
    281    case 17: VG_(transfer) (&mips1->guest_r17, buf, dir, size, mod); break;
    282    case 18: VG_(transfer) (&mips1->guest_r18,  buf, dir, size, mod); break;
    283    case 19: VG_(transfer) (&mips1->guest_r19,  buf, dir, size, mod); break;
    284    case 20: VG_(transfer) (&mips1->guest_r20,  buf, dir, size, mod); break;
    285    case 21: VG_(transfer) (&mips1->guest_r21,  buf, dir, size, mod); break;
    286    case 22: VG_(transfer) (&mips1->guest_r22,  buf, dir, size, mod); break;
    287    case 23: VG_(transfer) (&mips1->guest_r23,  buf, dir, size, mod); break;
    288    case 24: VG_(transfer) (&mips1->guest_r24,  buf, dir, size, mod); break;
    289    case 25: VG_(transfer) (&mips1->guest_r25,  buf, dir, size, mod); break;
    290    case 26: VG_(transfer) (&mips1->guest_r26,  buf, dir, size, mod); break;
    291    case 27: VG_(transfer) (&mips1->guest_r27,  buf, dir, size, mod); break;
    292    case 28: VG_(transfer) (&mips1->guest_r28, buf, dir, size, mod); break;
    293    case 29: VG_(transfer) (&mips1->guest_r29, buf, dir, size, mod); break;
    294    case 30: VG_(transfer) (&mips1->guest_r30, buf, dir, size, mod); break;
    295    case 31: VG_(transfer) (&mips1->guest_r31, buf, dir, size, mod); break;
    296    case 32: *mod = False; break; // GDBTD???? VEX { "status", 1024, 64 }
    297    case 33: VG_(transfer) (&mips1->guest_LO, buf, dir, size, mod); break;
    298    case 34: VG_(transfer) (&mips1->guest_HI, buf, dir, size, mod); break;
    299    case 35: *mod = False; break; // GDBTD???? VEX { "badvaddr", 1120, 64 },
    300    case 36: *mod = False; break; // GDBTD???? VEX { "cause", 1152, 64 },
    301    case 37:
    302       /* If a breakpoint is set on the instruction in a branch delay slot,
    303          GDB gets confused.  When the breakpoint is hit, the PC isn't on
    304          the instruction in the branch delay slot, the PC will point to
    305          the branch instruction. */
    306       mips1->guest_PC = mips_adjust_breakpoint_address(mips1->guest_PC);
    307       VG_(transfer) (&mips1->guest_PC,  buf, dir, size, mod);
    308       break;
    309    case 38: VG_(transfer) (&mips1->guest_f0,  buf, dir, size, mod); break;
    310    case 39: VG_(transfer) (&mips1->guest_f1,  buf, dir, size, mod); break;
    311    case 40: VG_(transfer) (&mips1->guest_f2,  buf, dir, size, mod); break;
    312    case 41: VG_(transfer) (&mips1->guest_f3,  buf, dir, size, mod); break;
    313    case 42: VG_(transfer) (&mips1->guest_f4,  buf, dir, size, mod); break;
    314    case 43: VG_(transfer) (&mips1->guest_f5,  buf, dir, size, mod); break;
    315    case 44: VG_(transfer) (&mips1->guest_f6,  buf, dir, size, mod); break;
    316    case 45: VG_(transfer) (&mips1->guest_f7, buf, dir, size, mod); break;
    317    case 46: VG_(transfer) (&mips1->guest_f8, buf, dir, size, mod); break;
    318    case 47: VG_(transfer) (&mips1->guest_f9, buf, dir, size, mod); break;
    319    case 48: VG_(transfer) (&mips1->guest_f10, buf, dir, size, mod); break;
    320    case 49: VG_(transfer) (&mips1->guest_f11, buf, dir, size, mod); break;
    321    case 50: VG_(transfer) (&mips1->guest_f12, buf, dir, size, mod); break;
    322    case 51: VG_(transfer) (&mips1->guest_f13,  buf, dir, size, mod); break;
    323    case 52: VG_(transfer) (&mips1->guest_f14,  buf, dir, size, mod); break;
    324    case 53: VG_(transfer) (&mips1->guest_f15,  buf, dir, size, mod); break;
    325    case 54: VG_(transfer) (&mips1->guest_f16,  buf, dir, size, mod); break;
    326    case 55: VG_(transfer) (&mips1->guest_f17,  buf, dir, size, mod); break;
    327    case 56: VG_(transfer) (&mips1->guest_f18,  buf, dir, size, mod); break;
    328    case 57: VG_(transfer) (&mips1->guest_f19, buf, dir, size, mod); break;
    329    case 58: VG_(transfer) (&mips1->guest_f20, buf, dir, size, mod); break;
    330    case 59: VG_(transfer) (&mips1->guest_f21, buf, dir, size, mod); break;
    331    case 60: VG_(transfer) (&mips1->guest_f22, buf, dir, size, mod); break;
    332    case 61: VG_(transfer) (&mips1->guest_f23, buf, dir, size, mod); break;
    333    case 62: VG_(transfer) (&mips1->guest_f24,  buf, dir, size, mod); break;
    334    case 63: VG_(transfer) (&mips1->guest_f25,  buf, dir, size, mod); break;
    335    case 64: VG_(transfer) (&mips1->guest_f26,  buf, dir, size, mod); break;
    336    case 65: VG_(transfer) (&mips1->guest_f27,  buf, dir, size, mod); break;
    337    case 66: VG_(transfer) (&mips1->guest_f28,  buf, dir, size, mod); break;
    338    case 67: VG_(transfer) (&mips1->guest_f29,  buf, dir, size, mod); break;
    339    case 68: VG_(transfer) (&mips1->guest_f30, buf, dir, size, mod); break;
    340    case 69: VG_(transfer) (&mips1->guest_f31, buf, dir, size, mod); break;
    341    case 70: VG_(transfer) (&mips1->guest_FCSR, buf, dir, size, mod); break;
    342    case 71: VG_(transfer) (&mips1->guest_FIR, buf, dir, size, mod); break;
    343    case 72: *mod = False; break; // GDBTD???? VEX{ "restart", 2304, 64 },
    344    default: VG_(printf)("regno: %d\n", regno); vg_assert(0);
    345    }
    346 }
    347 
    348 static
    349 const char* target_xml (Bool shadow_mode)
    350 {
    351    if (shadow_mode) {
    352       return "mips64-linux-valgrind.xml";
    353    } else {
    354       return "mips64-linux.xml";
    355    }
    356 }
    357 
    358 static struct valgrind_target_ops low_target = {
    359    num_regs,
    360    regs,
    361    29, //sp = r29, which is register offset 29 in regs
    362    transfer_register,
    363    get_pc,
    364    set_pc,
    365    "mips64",
    366    target_xml
    367 };
    368 
    369 void mips64_init_architecture (struct valgrind_target_ops *target)
    370 {
    371    *target = low_target;
    372    set_register_cache (regs, num_regs);
    373    gdbserver_expedite_regs = expedite_regs;
    374 }
    375