EmulateInstructionMIPS.cpp revision 360784
1//===-- EmulateInstructionMIPS.cpp -------------------------------*- C++-*-===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8
9#include "EmulateInstructionMIPS.h"
10
11#include <stdlib.h>
12
13#include "lldb/Core/Address.h"
14#include "lldb/Core/Opcode.h"
15#include "lldb/Core/PluginManager.h"
16#include "lldb/Symbol/UnwindPlan.h"
17#include "lldb/Target/Target.h"
18#include "lldb/Utility/ArchSpec.h"
19#include "lldb/Utility/ConstString.h"
20#include "lldb/Utility/DataExtractor.h"
21#include "lldb/Utility/RegisterValue.h"
22#include "lldb/Utility/Stream.h"
23#include "llvm-c/Disassembler.h"
24#include "llvm/MC/MCAsmInfo.h"
25#include "llvm/MC/MCContext.h"
26#include "llvm/MC/MCDisassembler/MCDisassembler.h"
27#include "llvm/MC/MCInst.h"
28#include "llvm/MC/MCInstrInfo.h"
29#include "llvm/MC/MCRegisterInfo.h"
30#include "llvm/MC/MCSubtargetInfo.h"
31#include "llvm/MC/MCTargetOptions.h"
32#include "llvm/Support/TargetRegistry.h"
33#include "llvm/Support/TargetSelect.h"
34
35#include "llvm/ADT/STLExtras.h"
36
37#include "Plugins/Process/Utility/InstructionUtils.h"
38#include "Plugins/Process/Utility/RegisterContext_mips.h"
39
40using namespace lldb;
41using namespace lldb_private;
42
43#define UInt(x) ((uint64_t)x)
44#define integer int64_t
45
46//
47// EmulateInstructionMIPS implementation
48//
49
50#ifdef __mips__
51extern "C" {
52void LLVMInitializeMipsTargetInfo();
53void LLVMInitializeMipsTarget();
54void LLVMInitializeMipsAsmPrinter();
55void LLVMInitializeMipsTargetMC();
56void LLVMInitializeMipsDisassembler();
57}
58#endif
59
60EmulateInstructionMIPS::EmulateInstructionMIPS(
61    const lldb_private::ArchSpec &arch)
62    : EmulateInstruction(arch) {
63  /* Create instance of llvm::MCDisassembler */
64  std::string Status;
65  llvm::Triple triple = arch.GetTriple();
66  const llvm::Target *target =
67      llvm::TargetRegistry::lookupTarget(triple.getTriple(), Status);
68
69/*
70 * If we fail to get the target then we haven't registered it. The
71 * SystemInitializerCommon
72 * does not initialize targets, MCs and disassemblers. However we need the
73 * MCDisassembler
74 * to decode the instructions so that the decoding complexity stays with LLVM.
75 * Initialize the MIPS targets and disassemblers.
76*/
77#ifdef __mips__
78  if (!target) {
79    LLVMInitializeMipsTargetInfo();
80    LLVMInitializeMipsTarget();
81    LLVMInitializeMipsAsmPrinter();
82    LLVMInitializeMipsTargetMC();
83    LLVMInitializeMipsDisassembler();
84    target = llvm::TargetRegistry::lookupTarget(triple.getTriple(), Status);
85  }
86#endif
87
88  assert(target);
89
90  llvm::StringRef cpu;
91
92  switch (arch.GetCore()) {
93  case ArchSpec::eCore_mips32:
94  case ArchSpec::eCore_mips32el:
95    cpu = "mips32";
96    break;
97  case ArchSpec::eCore_mips32r2:
98  case ArchSpec::eCore_mips32r2el:
99    cpu = "mips32r2";
100    break;
101  case ArchSpec::eCore_mips32r3:
102  case ArchSpec::eCore_mips32r3el:
103    cpu = "mips32r3";
104    break;
105  case ArchSpec::eCore_mips32r5:
106  case ArchSpec::eCore_mips32r5el:
107    cpu = "mips32r5";
108    break;
109  case ArchSpec::eCore_mips32r6:
110  case ArchSpec::eCore_mips32r6el:
111    cpu = "mips32r6";
112    break;
113  case ArchSpec::eCore_mips64:
114  case ArchSpec::eCore_mips64el:
115    cpu = "mips64";
116    break;
117  case ArchSpec::eCore_mips64r2:
118  case ArchSpec::eCore_mips64r2el:
119    cpu = "mips64r2";
120    break;
121  case ArchSpec::eCore_mips64r3:
122  case ArchSpec::eCore_mips64r3el:
123    cpu = "mips64r3";
124    break;
125  case ArchSpec::eCore_mips64r5:
126  case ArchSpec::eCore_mips64r5el:
127    cpu = "mips64r5";
128    break;
129  case ArchSpec::eCore_mips64r6:
130  case ArchSpec::eCore_mips64r6el:
131    cpu = "mips64r6";
132    break;
133  default:
134    cpu = "generic";
135    break;
136  }
137
138  std::string features = "";
139  uint32_t arch_flags = arch.GetFlags();
140  if (arch_flags & ArchSpec::eMIPSAse_msa)
141    features += "+msa,";
142  if (arch_flags & ArchSpec::eMIPSAse_dsp)
143    features += "+dsp,";
144  if (arch_flags & ArchSpec::eMIPSAse_dspr2)
145    features += "+dspr2,";
146
147  m_reg_info.reset(target->createMCRegInfo(triple.getTriple()));
148  assert(m_reg_info.get());
149
150  m_insn_info.reset(target->createMCInstrInfo());
151  assert(m_insn_info.get());
152
153  llvm::MCTargetOptions MCOptions;
154  m_asm_info.reset(
155      target->createMCAsmInfo(*m_reg_info, triple.getTriple(), MCOptions));
156  m_subtype_info.reset(
157      target->createMCSubtargetInfo(triple.getTriple(), cpu, features));
158  assert(m_asm_info.get() && m_subtype_info.get());
159
160  m_context.reset(
161      new llvm::MCContext(m_asm_info.get(), m_reg_info.get(), nullptr));
162  assert(m_context.get());
163
164  m_disasm.reset(target->createMCDisassembler(*m_subtype_info, *m_context));
165  assert(m_disasm.get());
166
167  /* Create alternate disassembler for microMIPS */
168  if (arch_flags & ArchSpec::eMIPSAse_mips16)
169    features += "+mips16,";
170  else if (arch_flags & ArchSpec::eMIPSAse_micromips)
171    features += "+micromips,";
172
173  m_alt_subtype_info.reset(
174      target->createMCSubtargetInfo(triple.getTriple(), cpu, features));
175  assert(m_alt_subtype_info.get());
176
177  m_alt_disasm.reset(
178      target->createMCDisassembler(*m_alt_subtype_info, *m_context));
179  assert(m_alt_disasm.get());
180
181  m_next_inst_size = 0;
182  m_use_alt_disaasm = false;
183}
184
185void EmulateInstructionMIPS::Initialize() {
186  PluginManager::RegisterPlugin(GetPluginNameStatic(),
187                                GetPluginDescriptionStatic(), CreateInstance);
188}
189
190void EmulateInstructionMIPS::Terminate() {
191  PluginManager::UnregisterPlugin(CreateInstance);
192}
193
194ConstString EmulateInstructionMIPS::GetPluginNameStatic() {
195  ConstString g_plugin_name("lldb.emulate-instruction.mips32");
196  return g_plugin_name;
197}
198
199lldb_private::ConstString EmulateInstructionMIPS::GetPluginName() {
200  static ConstString g_plugin_name("EmulateInstructionMIPS");
201  return g_plugin_name;
202}
203
204const char *EmulateInstructionMIPS::GetPluginDescriptionStatic() {
205  return "Emulate instructions for the MIPS32 architecture.";
206}
207
208EmulateInstruction *
209EmulateInstructionMIPS::CreateInstance(const ArchSpec &arch,
210                                       InstructionType inst_type) {
211  if (EmulateInstructionMIPS::SupportsEmulatingInstructionsOfTypeStatic(
212          inst_type)) {
213    if (arch.GetTriple().getArch() == llvm::Triple::mips ||
214        arch.GetTriple().getArch() == llvm::Triple::mipsel) {
215      return new EmulateInstructionMIPS(arch);
216    }
217  }
218
219  return nullptr;
220}
221
222bool EmulateInstructionMIPS::SetTargetTriple(const ArchSpec &arch) {
223  return arch.GetTriple().getArch() == llvm::Triple::mips ||
224         arch.GetTriple().getArch() == llvm::Triple::mipsel;
225}
226
227const char *EmulateInstructionMIPS::GetRegisterName(unsigned reg_num,
228                                                    bool alternate_name) {
229  if (alternate_name) {
230    switch (reg_num) {
231    case dwarf_sp_mips:
232      return "r29";
233    case dwarf_r30_mips:
234      return "r30";
235    case dwarf_ra_mips:
236      return "r31";
237    case dwarf_f0_mips:
238      return "f0";
239    case dwarf_f1_mips:
240      return "f1";
241    case dwarf_f2_mips:
242      return "f2";
243    case dwarf_f3_mips:
244      return "f3";
245    case dwarf_f4_mips:
246      return "f4";
247    case dwarf_f5_mips:
248      return "f5";
249    case dwarf_f6_mips:
250      return "f6";
251    case dwarf_f7_mips:
252      return "f7";
253    case dwarf_f8_mips:
254      return "f8";
255    case dwarf_f9_mips:
256      return "f9";
257    case dwarf_f10_mips:
258      return "f10";
259    case dwarf_f11_mips:
260      return "f11";
261    case dwarf_f12_mips:
262      return "f12";
263    case dwarf_f13_mips:
264      return "f13";
265    case dwarf_f14_mips:
266      return "f14";
267    case dwarf_f15_mips:
268      return "f15";
269    case dwarf_f16_mips:
270      return "f16";
271    case dwarf_f17_mips:
272      return "f17";
273    case dwarf_f18_mips:
274      return "f18";
275    case dwarf_f19_mips:
276      return "f19";
277    case dwarf_f20_mips:
278      return "f20";
279    case dwarf_f21_mips:
280      return "f21";
281    case dwarf_f22_mips:
282      return "f22";
283    case dwarf_f23_mips:
284      return "f23";
285    case dwarf_f24_mips:
286      return "f24";
287    case dwarf_f25_mips:
288      return "f25";
289    case dwarf_f26_mips:
290      return "f26";
291    case dwarf_f27_mips:
292      return "f27";
293    case dwarf_f28_mips:
294      return "f28";
295    case dwarf_f29_mips:
296      return "f29";
297    case dwarf_f30_mips:
298      return "f30";
299    case dwarf_f31_mips:
300      return "f31";
301    case dwarf_w0_mips:
302      return "w0";
303    case dwarf_w1_mips:
304      return "w1";
305    case dwarf_w2_mips:
306      return "w2";
307    case dwarf_w3_mips:
308      return "w3";
309    case dwarf_w4_mips:
310      return "w4";
311    case dwarf_w5_mips:
312      return "w5";
313    case dwarf_w6_mips:
314      return "w6";
315    case dwarf_w7_mips:
316      return "w7";
317    case dwarf_w8_mips:
318      return "w8";
319    case dwarf_w9_mips:
320      return "w9";
321    case dwarf_w10_mips:
322      return "w10";
323    case dwarf_w11_mips:
324      return "w11";
325    case dwarf_w12_mips:
326      return "w12";
327    case dwarf_w13_mips:
328      return "w13";
329    case dwarf_w14_mips:
330      return "w14";
331    case dwarf_w15_mips:
332      return "w15";
333    case dwarf_w16_mips:
334      return "w16";
335    case dwarf_w17_mips:
336      return "w17";
337    case dwarf_w18_mips:
338      return "w18";
339    case dwarf_w19_mips:
340      return "w19";
341    case dwarf_w20_mips:
342      return "w20";
343    case dwarf_w21_mips:
344      return "w21";
345    case dwarf_w22_mips:
346      return "w22";
347    case dwarf_w23_mips:
348      return "w23";
349    case dwarf_w24_mips:
350      return "w24";
351    case dwarf_w25_mips:
352      return "w25";
353    case dwarf_w26_mips:
354      return "w26";
355    case dwarf_w27_mips:
356      return "w27";
357    case dwarf_w28_mips:
358      return "w28";
359    case dwarf_w29_mips:
360      return "w29";
361    case dwarf_w30_mips:
362      return "w30";
363    case dwarf_w31_mips:
364      return "w31";
365    case dwarf_mir_mips:
366      return "mir";
367    case dwarf_mcsr_mips:
368      return "mcsr";
369    case dwarf_config5_mips:
370      return "config5";
371    default:
372      break;
373    }
374    return nullptr;
375  }
376
377  switch (reg_num) {
378  case dwarf_zero_mips:
379    return "r0";
380  case dwarf_r1_mips:
381    return "r1";
382  case dwarf_r2_mips:
383    return "r2";
384  case dwarf_r3_mips:
385    return "r3";
386  case dwarf_r4_mips:
387    return "r4";
388  case dwarf_r5_mips:
389    return "r5";
390  case dwarf_r6_mips:
391    return "r6";
392  case dwarf_r7_mips:
393    return "r7";
394  case dwarf_r8_mips:
395    return "r8";
396  case dwarf_r9_mips:
397    return "r9";
398  case dwarf_r10_mips:
399    return "r10";
400  case dwarf_r11_mips:
401    return "r11";
402  case dwarf_r12_mips:
403    return "r12";
404  case dwarf_r13_mips:
405    return "r13";
406  case dwarf_r14_mips:
407    return "r14";
408  case dwarf_r15_mips:
409    return "r15";
410  case dwarf_r16_mips:
411    return "r16";
412  case dwarf_r17_mips:
413    return "r17";
414  case dwarf_r18_mips:
415    return "r18";
416  case dwarf_r19_mips:
417    return "r19";
418  case dwarf_r20_mips:
419    return "r20";
420  case dwarf_r21_mips:
421    return "r21";
422  case dwarf_r22_mips:
423    return "r22";
424  case dwarf_r23_mips:
425    return "r23";
426  case dwarf_r24_mips:
427    return "r24";
428  case dwarf_r25_mips:
429    return "r25";
430  case dwarf_r26_mips:
431    return "r26";
432  case dwarf_r27_mips:
433    return "r27";
434  case dwarf_gp_mips:
435    return "gp";
436  case dwarf_sp_mips:
437    return "sp";
438  case dwarf_r30_mips:
439    return "fp";
440  case dwarf_ra_mips:
441    return "ra";
442  case dwarf_sr_mips:
443    return "sr";
444  case dwarf_lo_mips:
445    return "lo";
446  case dwarf_hi_mips:
447    return "hi";
448  case dwarf_bad_mips:
449    return "bad";
450  case dwarf_cause_mips:
451    return "cause";
452  case dwarf_pc_mips:
453    return "pc";
454  case dwarf_f0_mips:
455    return "f0";
456  case dwarf_f1_mips:
457    return "f1";
458  case dwarf_f2_mips:
459    return "f2";
460  case dwarf_f3_mips:
461    return "f3";
462  case dwarf_f4_mips:
463    return "f4";
464  case dwarf_f5_mips:
465    return "f5";
466  case dwarf_f6_mips:
467    return "f6";
468  case dwarf_f7_mips:
469    return "f7";
470  case dwarf_f8_mips:
471    return "f8";
472  case dwarf_f9_mips:
473    return "f9";
474  case dwarf_f10_mips:
475    return "f10";
476  case dwarf_f11_mips:
477    return "f11";
478  case dwarf_f12_mips:
479    return "f12";
480  case dwarf_f13_mips:
481    return "f13";
482  case dwarf_f14_mips:
483    return "f14";
484  case dwarf_f15_mips:
485    return "f15";
486  case dwarf_f16_mips:
487    return "f16";
488  case dwarf_f17_mips:
489    return "f17";
490  case dwarf_f18_mips:
491    return "f18";
492  case dwarf_f19_mips:
493    return "f19";
494  case dwarf_f20_mips:
495    return "f20";
496  case dwarf_f21_mips:
497    return "f21";
498  case dwarf_f22_mips:
499    return "f22";
500  case dwarf_f23_mips:
501    return "f23";
502  case dwarf_f24_mips:
503    return "f24";
504  case dwarf_f25_mips:
505    return "f25";
506  case dwarf_f26_mips:
507    return "f26";
508  case dwarf_f27_mips:
509    return "f27";
510  case dwarf_f28_mips:
511    return "f28";
512  case dwarf_f29_mips:
513    return "f29";
514  case dwarf_f30_mips:
515    return "f30";
516  case dwarf_f31_mips:
517    return "f31";
518  case dwarf_fcsr_mips:
519    return "fcsr";
520  case dwarf_fir_mips:
521    return "fir";
522  case dwarf_w0_mips:
523    return "w0";
524  case dwarf_w1_mips:
525    return "w1";
526  case dwarf_w2_mips:
527    return "w2";
528  case dwarf_w3_mips:
529    return "w3";
530  case dwarf_w4_mips:
531    return "w4";
532  case dwarf_w5_mips:
533    return "w5";
534  case dwarf_w6_mips:
535    return "w6";
536  case dwarf_w7_mips:
537    return "w7";
538  case dwarf_w8_mips:
539    return "w8";
540  case dwarf_w9_mips:
541    return "w9";
542  case dwarf_w10_mips:
543    return "w10";
544  case dwarf_w11_mips:
545    return "w11";
546  case dwarf_w12_mips:
547    return "w12";
548  case dwarf_w13_mips:
549    return "w13";
550  case dwarf_w14_mips:
551    return "w14";
552  case dwarf_w15_mips:
553    return "w15";
554  case dwarf_w16_mips:
555    return "w16";
556  case dwarf_w17_mips:
557    return "w17";
558  case dwarf_w18_mips:
559    return "w18";
560  case dwarf_w19_mips:
561    return "w19";
562  case dwarf_w20_mips:
563    return "w20";
564  case dwarf_w21_mips:
565    return "w21";
566  case dwarf_w22_mips:
567    return "w22";
568  case dwarf_w23_mips:
569    return "w23";
570  case dwarf_w24_mips:
571    return "w24";
572  case dwarf_w25_mips:
573    return "w25";
574  case dwarf_w26_mips:
575    return "w26";
576  case dwarf_w27_mips:
577    return "w27";
578  case dwarf_w28_mips:
579    return "w28";
580  case dwarf_w29_mips:
581    return "w29";
582  case dwarf_w30_mips:
583    return "w30";
584  case dwarf_w31_mips:
585    return "w31";
586  case dwarf_mcsr_mips:
587    return "mcsr";
588  case dwarf_mir_mips:
589    return "mir";
590  case dwarf_config5_mips:
591    return "config5";
592  }
593  return nullptr;
594}
595
596bool EmulateInstructionMIPS::GetRegisterInfo(RegisterKind reg_kind,
597                                             uint32_t reg_num,
598                                             RegisterInfo &reg_info) {
599  if (reg_kind == eRegisterKindGeneric) {
600    switch (reg_num) {
601    case LLDB_REGNUM_GENERIC_PC:
602      reg_kind = eRegisterKindDWARF;
603      reg_num = dwarf_pc_mips;
604      break;
605    case LLDB_REGNUM_GENERIC_SP:
606      reg_kind = eRegisterKindDWARF;
607      reg_num = dwarf_sp_mips;
608      break;
609    case LLDB_REGNUM_GENERIC_FP:
610      reg_kind = eRegisterKindDWARF;
611      reg_num = dwarf_r30_mips;
612      break;
613    case LLDB_REGNUM_GENERIC_RA:
614      reg_kind = eRegisterKindDWARF;
615      reg_num = dwarf_ra_mips;
616      break;
617    case LLDB_REGNUM_GENERIC_FLAGS:
618      reg_kind = eRegisterKindDWARF;
619      reg_num = dwarf_sr_mips;
620      break;
621    default:
622      return false;
623    }
624  }
625
626  if (reg_kind == eRegisterKindDWARF) {
627    ::memset(&reg_info, 0, sizeof(RegisterInfo));
628    ::memset(reg_info.kinds, LLDB_INVALID_REGNUM, sizeof(reg_info.kinds));
629
630    if (reg_num == dwarf_sr_mips || reg_num == dwarf_fcsr_mips ||
631        reg_num == dwarf_fir_mips || reg_num == dwarf_mcsr_mips ||
632        reg_num == dwarf_mir_mips || reg_num == dwarf_config5_mips) {
633      reg_info.byte_size = 4;
634      reg_info.format = eFormatHex;
635      reg_info.encoding = eEncodingUint;
636    } else if ((int)reg_num >= dwarf_zero_mips &&
637               (int)reg_num <= dwarf_f31_mips) {
638      reg_info.byte_size = 4;
639      reg_info.format = eFormatHex;
640      reg_info.encoding = eEncodingUint;
641    } else if ((int)reg_num >= dwarf_w0_mips &&
642               (int)reg_num <= dwarf_w31_mips) {
643      reg_info.byte_size = 16;
644      reg_info.format = eFormatVectorOfUInt8;
645      reg_info.encoding = eEncodingVector;
646    } else {
647      return false;
648    }
649
650    reg_info.name = GetRegisterName(reg_num, false);
651    reg_info.alt_name = GetRegisterName(reg_num, true);
652    reg_info.kinds[eRegisterKindDWARF] = reg_num;
653
654    switch (reg_num) {
655    case dwarf_r30_mips:
656      reg_info.kinds[eRegisterKindGeneric] = LLDB_REGNUM_GENERIC_FP;
657      break;
658    case dwarf_ra_mips:
659      reg_info.kinds[eRegisterKindGeneric] = LLDB_REGNUM_GENERIC_RA;
660      break;
661    case dwarf_sp_mips:
662      reg_info.kinds[eRegisterKindGeneric] = LLDB_REGNUM_GENERIC_SP;
663      break;
664    case dwarf_pc_mips:
665      reg_info.kinds[eRegisterKindGeneric] = LLDB_REGNUM_GENERIC_PC;
666      break;
667    case dwarf_sr_mips:
668      reg_info.kinds[eRegisterKindGeneric] = LLDB_REGNUM_GENERIC_FLAGS;
669      break;
670    default:
671      break;
672    }
673    return true;
674  }
675  return false;
676}
677
678EmulateInstructionMIPS::MipsOpcode *
679EmulateInstructionMIPS::GetOpcodeForInstruction(const char *op_name) {
680  static EmulateInstructionMIPS::MipsOpcode g_opcodes[] = {
681      // Prologue/Epilogue instructions
682      {"ADDiu", &EmulateInstructionMIPS::Emulate_ADDiu,
683       "ADDIU rt, rs, immediate"},
684      {"SW", &EmulateInstructionMIPS::Emulate_SW, "SW rt, offset(rs)"},
685      {"LW", &EmulateInstructionMIPS::Emulate_LW, "LW rt, offset(base)"},
686      {"SUBU", &EmulateInstructionMIPS::Emulate_SUBU_ADDU, "SUBU rd, rs, rt"},
687      {"ADDU", &EmulateInstructionMIPS::Emulate_SUBU_ADDU, "ADDU rd, rs, rt"},
688      {"LUI", &EmulateInstructionMIPS::Emulate_LUI, "LUI rt, immediate"},
689
690      // MicroMIPS Prologue/Epilogue instructions
691      {"ADDIUSP_MM", &EmulateInstructionMIPS::Emulate_ADDIUSP,
692       "ADDIU immediate"},
693      {"ADDIUS5_MM", &EmulateInstructionMIPS::Emulate_ADDIUS5,
694       "ADDIUS5 rd,immediate"},
695      {"SWSP_MM", &EmulateInstructionMIPS::Emulate_SWSP, "SWSP rt,offset(sp)"},
696      {"SWM16_MM", &EmulateInstructionMIPS::Emulate_SWM16_32,
697       "SWM16 reglist,offset(sp)"},
698      {"SWM32_MM", &EmulateInstructionMIPS::Emulate_SWM16_32,
699       "SWM32 reglist,offset(base)"},
700      {"SWP_MM", &EmulateInstructionMIPS::Emulate_SWM16_32,
701       "SWP rs1,offset(base)"},
702      {"LWSP_MM", &EmulateInstructionMIPS::Emulate_LWSP, "LWSP rt,offset(sp)"},
703      {"LWM16_MM", &EmulateInstructionMIPS::Emulate_LWM16_32,
704       "LWM16 reglist,offset(sp)"},
705      {"LWM32_MM", &EmulateInstructionMIPS::Emulate_LWM16_32,
706       "LWM32 reglist,offset(base)"},
707      {"LWP_MM", &EmulateInstructionMIPS::Emulate_LWM16_32,
708       "LWP rd,offset(base)"},
709      {"JRADDIUSP", &EmulateInstructionMIPS::Emulate_JRADDIUSP,
710       "JRADDIUSP immediate"},
711
712      // Load/Store  instructions
713      /* Following list of emulated instructions are required by implementation
714         of hardware watchpoint
715         for MIPS in lldb. As we just need the address accessed by instructions,
716         we have generalised
717         all these instructions in 2 functions depending on their addressing
718         modes */
719
720      {"LB", &EmulateInstructionMIPS::Emulate_LDST_Imm,
721       "LB    rt, offset(base)"},
722      {"LBE", &EmulateInstructionMIPS::Emulate_LDST_Imm,
723       "LBE   rt, offset(base)"},
724      {"LBU", &EmulateInstructionMIPS::Emulate_LDST_Imm,
725       "LBU   rt, offset(base)"},
726      {"LBUE", &EmulateInstructionMIPS::Emulate_LDST_Imm,
727       "LBUE  rt, offset(base)"},
728      {"LDC1", &EmulateInstructionMIPS::Emulate_LDST_Imm,
729       "LDC1  ft, offset(base)"},
730      {"LD", &EmulateInstructionMIPS::Emulate_LDST_Imm,
731       "LD    rt, offset(base)"},
732      {"LDL", &EmulateInstructionMIPS::Emulate_LDST_Imm,
733       "LDL   rt, offset(base)"},
734      {"LDR", &EmulateInstructionMIPS::Emulate_LDST_Imm,
735       "LDR   rt, offset(base)"},
736      {"LLD", &EmulateInstructionMIPS::Emulate_LDST_Imm,
737       "LLD   rt, offset(base)"},
738      {"LDC2", &EmulateInstructionMIPS::Emulate_LDST_Imm,
739       "LDC2  rt, offset(base)"},
740      {"LDXC1", &EmulateInstructionMIPS::Emulate_LDST_Reg,
741       "LDXC1 fd, index (base)"},
742      {"LH", &EmulateInstructionMIPS::Emulate_LDST_Imm,
743       "LH    rt, offset(base)"},
744      {"LHE", &EmulateInstructionMIPS::Emulate_LDST_Imm,
745       "LHE   rt, offset(base)"},
746      {"LHU", &EmulateInstructionMIPS::Emulate_LDST_Imm,
747       "LHU   rt, offset(base)"},
748      {"LHUE", &EmulateInstructionMIPS::Emulate_LDST_Imm,
749       "LHUE  rt, offset(base)"},
750      {"LL", &EmulateInstructionMIPS::Emulate_LDST_Imm,
751       "LL    rt, offset(base)"},
752      {"LLE", &EmulateInstructionMIPS::Emulate_LDST_Imm,
753       "LLE   rt, offset(base)"},
754      {"LUXC1", &EmulateInstructionMIPS::Emulate_LDST_Reg,
755       "LUXC1 fd, index (base)"},
756      {"LW", &EmulateInstructionMIPS::Emulate_LDST_Imm,
757       "LW    rt, offset(base)"},
758      {"LWC1", &EmulateInstructionMIPS::Emulate_LDST_Imm,
759       "LWC1  ft, offset(base)"},
760      {"LWC2", &EmulateInstructionMIPS::Emulate_LDST_Imm,
761       "LWC2  rt, offset(base)"},
762      {"LWE", &EmulateInstructionMIPS::Emulate_LDST_Imm,
763       "LWE   rt, offset(base)"},
764      {"LWL", &EmulateInstructionMIPS::Emulate_LDST_Imm,
765       "LWL   rt, offset(base)"},
766      {"LWLE", &EmulateInstructionMIPS::Emulate_LDST_Imm,
767       "LWLE  rt, offset(base)"},
768      {"LWR", &EmulateInstructionMIPS::Emulate_LDST_Imm,
769       "LWR   rt, offset(base)"},
770      {"LWRE", &EmulateInstructionMIPS::Emulate_LDST_Imm,
771       "LWRE  rt, offset(base)"},
772      {"LWXC1", &EmulateInstructionMIPS::Emulate_LDST_Reg,
773       "LWXC1 fd, index (base)"},
774      {"LLX", &EmulateInstructionMIPS::Emulate_LDST_Imm,
775       "LLX   rt, offset(base)"},
776      {"LLXE", &EmulateInstructionMIPS::Emulate_LDST_Imm,
777       "LLXE  rt, offset(base)"},
778      {"LLDX", &EmulateInstructionMIPS::Emulate_LDST_Imm,
779       "LLDX  rt, offset(base)"},
780
781      {"SB", &EmulateInstructionMIPS::Emulate_LDST_Imm,
782       "SB    rt, offset(base)"},
783      {"SBE", &EmulateInstructionMIPS::Emulate_LDST_Imm,
784       "SBE   rt, offset(base)"},
785      {"SC", &EmulateInstructionMIPS::Emulate_LDST_Imm,
786       "SC    rt, offset(base)"},
787      {"SCE", &EmulateInstructionMIPS::Emulate_LDST_Imm,
788       "SCE   rt, offset(base)"},
789      {"SCD", &EmulateInstructionMIPS::Emulate_LDST_Imm,
790       "SCD   rt, offset(base)"},
791      {"SD", &EmulateInstructionMIPS::Emulate_LDST_Imm,
792       "SD    rt, offset(base)"},
793      {"SDL", &EmulateInstructionMIPS::Emulate_LDST_Imm,
794       "SDL   rt, offset(base)"},
795      {"SDR", &EmulateInstructionMIPS::Emulate_LDST_Imm,
796       "SDR   rt, offset(base)"},
797      {"SDC1", &EmulateInstructionMIPS::Emulate_LDST_Imm,
798       "SDC1  ft, offset(base)"},
799      {"SDC2", &EmulateInstructionMIPS::Emulate_LDST_Imm,
800       "SDC2  rt, offset(base)"},
801      {"SDXC1", &EmulateInstructionMIPS::Emulate_LDST_Reg,
802       "SDXC1 fs, index(base)"},
803      {"SH", &EmulateInstructionMIPS::Emulate_LDST_Imm,
804       "SH    rt, offset(base)"},
805      {"SHE", &EmulateInstructionMIPS::Emulate_LDST_Imm,
806       "SHE   rt, offset(base)"},
807      {"SUXC1", &EmulateInstructionMIPS::Emulate_LDST_Reg,
808       "SUXC1 fs, index (base)"},
809      {"SWC1", &EmulateInstructionMIPS::Emulate_LDST_Imm,
810       "SWC1  ft, offset(base)"},
811      {"SWC2", &EmulateInstructionMIPS::Emulate_LDST_Imm,
812       "SWC2  rt, offset(base)"},
813      {"SWE", &EmulateInstructionMIPS::Emulate_LDST_Imm,
814       "SWE   rt, offset(base)"},
815      {"SWL", &EmulateInstructionMIPS::Emulate_LDST_Imm,
816       "SWL   rt, offset(base)"},
817      {"SWLE", &EmulateInstructionMIPS::Emulate_LDST_Imm,
818       "SWLE  rt, offset(base)"},
819      {"SWR", &EmulateInstructionMIPS::Emulate_LDST_Imm,
820       "SWR   rt, offset(base)"},
821      {"SWRE", &EmulateInstructionMIPS::Emulate_LDST_Imm,
822       "SWRE  rt, offset(base)"},
823      {"SWXC1", &EmulateInstructionMIPS::Emulate_LDST_Reg,
824       "SWXC1 fs, index (base)"},
825      {"SCX", &EmulateInstructionMIPS::Emulate_LDST_Imm,
826       "SCX   rt, offset(base)"},
827      {"SCXE", &EmulateInstructionMIPS::Emulate_LDST_Imm,
828       "SCXE  rt, offset(base)"},
829      {"SCDX", &EmulateInstructionMIPS::Emulate_LDST_Imm,
830       "SCDX  rt, offset(base)"},
831
832      // MicroMIPS Load/Store instructions
833      {"LBU16_MM", &EmulateInstructionMIPS::Emulate_LDST_Imm,
834       "LBU16 rt, decoded_offset(base)"},
835      {"LHU16_MM", &EmulateInstructionMIPS::Emulate_LDST_Imm,
836       "LHU16 rt, left_shifted_offset(base)"},
837      {"LW16_MM", &EmulateInstructionMIPS::Emulate_LDST_Imm,
838       "LW16  rt, left_shifted_offset(base)"},
839      {"LWGP_MM", &EmulateInstructionMIPS::Emulate_LDST_Imm,
840       "LWGP  rt, left_shifted_offset(gp)"},
841      {"SH16_MM", &EmulateInstructionMIPS::Emulate_LDST_Imm,
842       "SH16  rt, left_shifted_offset(base)"},
843      {"SW16_MM", &EmulateInstructionMIPS::Emulate_LDST_Imm,
844       "SW16  rt, left_shifted_offset(base)"},
845      {"SW_MM", &EmulateInstructionMIPS::Emulate_LDST_Imm,
846       "SWSP  rt, left_shifted_offset(base)"},
847      {"SB16_MM", &EmulateInstructionMIPS::Emulate_LDST_Imm,
848       "SB16  rt, offset(base)"},
849
850      // Branch instructions
851      {"BEQ", &EmulateInstructionMIPS::Emulate_BXX_3ops, "BEQ rs,rt,offset"},
852      {"BNE", &EmulateInstructionMIPS::Emulate_BXX_3ops, "BNE rs,rt,offset"},
853      {"BEQL", &EmulateInstructionMIPS::Emulate_BXX_3ops, "BEQL rs,rt,offset"},
854      {"BNEL", &EmulateInstructionMIPS::Emulate_BXX_3ops, "BNEL rs,rt,offset"},
855      {"BGEZALL", &EmulateInstructionMIPS::Emulate_Bcond_Link,
856       "BGEZALL rt,offset"},
857      {"BAL", &EmulateInstructionMIPS::Emulate_BAL, "BAL offset"},
858      {"BGEZAL", &EmulateInstructionMIPS::Emulate_Bcond_Link,
859       "BGEZAL rs,offset"},
860      {"BALC", &EmulateInstructionMIPS::Emulate_BALC, "BALC offset"},
861      {"BC", &EmulateInstructionMIPS::Emulate_BC, "BC offset"},
862      {"BGEZ", &EmulateInstructionMIPS::Emulate_BXX_2ops, "BGEZ rs,offset"},
863      {"BLEZALC", &EmulateInstructionMIPS::Emulate_Bcond_Link_C,
864       "BLEZALC rs,offset"},
865      {"BGEZALC", &EmulateInstructionMIPS::Emulate_Bcond_Link_C,
866       "BGEZALC rs,offset"},
867      {"BLTZALC", &EmulateInstructionMIPS::Emulate_Bcond_Link_C,
868       "BLTZALC rs,offset"},
869      {"BGTZALC", &EmulateInstructionMIPS::Emulate_Bcond_Link_C,
870       "BGTZALC rs,offset"},
871      {"BEQZALC", &EmulateInstructionMIPS::Emulate_Bcond_Link_C,
872       "BEQZALC rs,offset"},
873      {"BNEZALC", &EmulateInstructionMIPS::Emulate_Bcond_Link_C,
874       "BNEZALC rs,offset"},
875      {"BEQC", &EmulateInstructionMIPS::Emulate_BXX_3ops_C,
876       "BEQC rs,rt,offset"},
877      {"BNEC", &EmulateInstructionMIPS::Emulate_BXX_3ops_C,
878       "BNEC rs,rt,offset"},
879      {"BLTC", &EmulateInstructionMIPS::Emulate_BXX_3ops_C,
880       "BLTC rs,rt,offset"},
881      {"BGEC", &EmulateInstructionMIPS::Emulate_BXX_3ops_C,
882       "BGEC rs,rt,offset"},
883      {"BLTUC", &EmulateInstructionMIPS::Emulate_BXX_3ops_C,
884       "BLTUC rs,rt,offset"},
885      {"BGEUC", &EmulateInstructionMIPS::Emulate_BXX_3ops_C,
886       "BGEUC rs,rt,offset"},
887      {"BLTZC", &EmulateInstructionMIPS::Emulate_BXX_2ops_C, "BLTZC rt,offset"},
888      {"BLEZC", &EmulateInstructionMIPS::Emulate_BXX_2ops_C, "BLEZC rt,offset"},
889      {"BGEZC", &EmulateInstructionMIPS::Emulate_BXX_2ops_C, "BGEZC rt,offset"},
890      {"BGTZC", &EmulateInstructionMIPS::Emulate_BXX_2ops_C, "BGTZC rt,offset"},
891      {"BEQZC", &EmulateInstructionMIPS::Emulate_BXX_2ops_C, "BEQZC rt,offset"},
892      {"BNEZC", &EmulateInstructionMIPS::Emulate_BXX_2ops_C, "BNEZC rt,offset"},
893      {"BGEZL", &EmulateInstructionMIPS::Emulate_BXX_2ops, "BGEZL rt,offset"},
894      {"BGTZ", &EmulateInstructionMIPS::Emulate_BXX_2ops, "BGTZ rt,offset"},
895      {"BGTZL", &EmulateInstructionMIPS::Emulate_BXX_2ops, "BGTZL rt,offset"},
896      {"BLEZ", &EmulateInstructionMIPS::Emulate_BXX_2ops, "BLEZ rt,offset"},
897      {"BLEZL", &EmulateInstructionMIPS::Emulate_BXX_2ops, "BLEZL rt,offset"},
898      {"BLTZ", &EmulateInstructionMIPS::Emulate_BXX_2ops, "BLTZ rt,offset"},
899      {"BLTZAL", &EmulateInstructionMIPS::Emulate_Bcond_Link,
900       "BLTZAL rt,offset"},
901      {"BLTZALL", &EmulateInstructionMIPS::Emulate_Bcond_Link,
902       "BLTZALL rt,offset"},
903      {"BLTZL", &EmulateInstructionMIPS::Emulate_BXX_2ops, "BLTZL rt,offset"},
904      {"BOVC", &EmulateInstructionMIPS::Emulate_BXX_3ops_C,
905       "BOVC rs,rt,offset"},
906      {"BNVC", &EmulateInstructionMIPS::Emulate_BXX_3ops_C,
907       "BNVC rs,rt,offset"},
908      {"J", &EmulateInstructionMIPS::Emulate_J, "J target"},
909      {"JAL", &EmulateInstructionMIPS::Emulate_JAL, "JAL target"},
910      {"JALX", &EmulateInstructionMIPS::Emulate_JAL, "JALX target"},
911      {"JALR", &EmulateInstructionMIPS::Emulate_JALR, "JALR target"},
912      {"JALR_HB", &EmulateInstructionMIPS::Emulate_JALR, "JALR.HB target"},
913      {"JIALC", &EmulateInstructionMIPS::Emulate_JIALC, "JIALC rt,offset"},
914      {"JIC", &EmulateInstructionMIPS::Emulate_JIC, "JIC rt,offset"},
915      {"JR", &EmulateInstructionMIPS::Emulate_JR, "JR target"},
916      {"JR_HB", &EmulateInstructionMIPS::Emulate_JR, "JR.HB target"},
917      {"BC1F", &EmulateInstructionMIPS::Emulate_FP_branch, "BC1F cc, offset"},
918      {"BC1T", &EmulateInstructionMIPS::Emulate_FP_branch, "BC1T cc, offset"},
919      {"BC1FL", &EmulateInstructionMIPS::Emulate_FP_branch, "BC1FL cc, offset"},
920      {"BC1TL", &EmulateInstructionMIPS::Emulate_FP_branch, "BC1TL cc, offset"},
921      {"BC1EQZ", &EmulateInstructionMIPS::Emulate_BC1EQZ, "BC1EQZ ft, offset"},
922      {"BC1NEZ", &EmulateInstructionMIPS::Emulate_BC1NEZ, "BC1NEZ ft, offset"},
923      {"BC1ANY2F", &EmulateInstructionMIPS::Emulate_3D_branch,
924       "BC1ANY2F cc, offset"},
925      {"BC1ANY2T", &EmulateInstructionMIPS::Emulate_3D_branch,
926       "BC1ANY2T cc, offset"},
927      {"BC1ANY4F", &EmulateInstructionMIPS::Emulate_3D_branch,
928       "BC1ANY4F cc, offset"},
929      {"BC1ANY4T", &EmulateInstructionMIPS::Emulate_3D_branch,
930       "BC1ANY4T cc, offset"},
931      {"BNZ_B", &EmulateInstructionMIPS::Emulate_BNZB, "BNZ.b wt,s16"},
932      {"BNZ_H", &EmulateInstructionMIPS::Emulate_BNZH, "BNZ.h wt,s16"},
933      {"BNZ_W", &EmulateInstructionMIPS::Emulate_BNZW, "BNZ.w wt,s16"},
934      {"BNZ_D", &EmulateInstructionMIPS::Emulate_BNZD, "BNZ.d wt,s16"},
935      {"BZ_B", &EmulateInstructionMIPS::Emulate_BZB, "BZ.b wt,s16"},
936      {"BZ_H", &EmulateInstructionMIPS::Emulate_BZH, "BZ.h wt,s16"},
937      {"BZ_W", &EmulateInstructionMIPS::Emulate_BZW, "BZ.w wt,s16"},
938      {"BZ_D", &EmulateInstructionMIPS::Emulate_BZD, "BZ.d wt,s16"},
939      {"BNZ_V", &EmulateInstructionMIPS::Emulate_BNZV, "BNZ.V wt,s16"},
940      {"BZ_V", &EmulateInstructionMIPS::Emulate_BZV, "BZ.V wt,s16"},
941
942      // MicroMIPS Branch instructions
943      {"B16_MM", &EmulateInstructionMIPS::Emulate_B16_MM, "B16 offset"},
944      {"BEQZ16_MM", &EmulateInstructionMIPS::Emulate_Branch_MM,
945       "BEQZ16 rs, offset"},
946      {"BNEZ16_MM", &EmulateInstructionMIPS::Emulate_Branch_MM,
947       "BNEZ16 rs, offset"},
948      {"BEQZC_MM", &EmulateInstructionMIPS::Emulate_Branch_MM,
949       "BEQZC rs, offset"},
950      {"BNEZC_MM", &EmulateInstructionMIPS::Emulate_Branch_MM,
951       "BNEZC rs, offset"},
952      {"BGEZALS_MM", &EmulateInstructionMIPS::Emulate_Branch_MM,
953       "BGEZALS rs, offset"},
954      {"BLTZALS_MM", &EmulateInstructionMIPS::Emulate_Branch_MM,
955       "BLTZALS rs, offset"},
956      {"JALR16_MM", &EmulateInstructionMIPS::Emulate_JALRx16_MM, "JALR16 rs"},
957      {"JALRS16_MM", &EmulateInstructionMIPS::Emulate_JALRx16_MM, "JALRS16 rs"},
958      {"JR16_MM", &EmulateInstructionMIPS::Emulate_JR, "JR16 rs rs"},
959      {"JRC16_MM", &EmulateInstructionMIPS::Emulate_JR, "JRC16 rs rs"},
960      {"JALS_MM", &EmulateInstructionMIPS::Emulate_JALx, "JALS target"},
961      {"JALX_MM", &EmulateInstructionMIPS::Emulate_JALx, "JALX target"},
962      {"JALRS_MM", &EmulateInstructionMIPS::Emulate_JALRS, "JALRS rt, rs"},
963  };
964
965  static const size_t k_num_mips_opcodes = llvm::array_lengthof(g_opcodes);
966
967  for (size_t i = 0; i < k_num_mips_opcodes; ++i) {
968    if (!strcasecmp(g_opcodes[i].op_name, op_name))
969      return &g_opcodes[i];
970  }
971
972  return nullptr;
973}
974
975uint32_t
976EmulateInstructionMIPS::GetSizeOfInstruction(lldb_private::DataExtractor &data,
977                                             uint64_t inst_addr) {
978  uint64_t next_inst_size = 0;
979  llvm::MCInst mc_insn;
980  llvm::MCDisassembler::DecodeStatus decode_status;
981  llvm::ArrayRef<uint8_t> raw_insn(data.GetDataStart(), data.GetByteSize());
982
983  if (m_use_alt_disaasm)
984    decode_status = m_alt_disasm->getInstruction(
985        mc_insn, next_inst_size, raw_insn, inst_addr, llvm::nulls());
986  else
987    decode_status = m_disasm->getInstruction(mc_insn, next_inst_size, raw_insn,
988                                             inst_addr, llvm::nulls());
989
990  if (decode_status != llvm::MCDisassembler::Success)
991    return false;
992
993  return m_insn_info->get(mc_insn.getOpcode()).getSize();
994}
995
996bool EmulateInstructionMIPS::SetInstruction(const Opcode &insn_opcode,
997                                            const Address &inst_addr,
998                                            Target *target) {
999  m_use_alt_disaasm = false;
1000
1001  if (EmulateInstruction::SetInstruction(insn_opcode, inst_addr, target)) {
1002    if (inst_addr.GetAddressClass() == AddressClass::eCodeAlternateISA) {
1003      Status error;
1004      lldb::addr_t load_addr = LLDB_INVALID_ADDRESS;
1005
1006      /*
1007       * The address belongs to microMIPS function. To find the size of
1008       * next instruction use microMIPS disassembler.
1009      */
1010      m_use_alt_disaasm = true;
1011
1012      uint32_t current_inst_size = insn_opcode.GetByteSize();
1013      uint8_t buf[sizeof(uint32_t)];
1014      uint64_t next_inst_addr = (m_addr & (~1ull)) + current_inst_size;
1015      Address next_addr(next_inst_addr);
1016
1017      const size_t bytes_read =
1018          target->ReadMemory(next_addr, /* Address of next instruction */
1019                             true,      /* prefer_file_cache */
1020                             buf, sizeof(uint32_t), error, &load_addr);
1021
1022      if (bytes_read == 0)
1023        return true;
1024
1025      DataExtractor data(buf, sizeof(uint32_t), GetByteOrder(),
1026                         GetAddressByteSize());
1027      m_next_inst_size = GetSizeOfInstruction(data, next_inst_addr);
1028      return true;
1029    } else {
1030      /*
1031       * If the address class is not AddressClass::eCodeAlternateISA then
1032       * the function is not microMIPS. In this case instruction size is
1033       * always 4 bytes.
1034      */
1035      m_next_inst_size = 4;
1036      return true;
1037    }
1038  }
1039  return false;
1040}
1041
1042bool EmulateInstructionMIPS::ReadInstruction() {
1043  bool success = false;
1044  m_addr = ReadRegisterUnsigned(eRegisterKindGeneric, LLDB_REGNUM_GENERIC_PC,
1045                                LLDB_INVALID_ADDRESS, &success);
1046  if (success) {
1047    Context read_inst_context;
1048    read_inst_context.type = eContextReadOpcode;
1049    read_inst_context.SetNoArgs();
1050    m_opcode.SetOpcode32(
1051        ReadMemoryUnsigned(read_inst_context, m_addr, 4, 0, &success),
1052        GetByteOrder());
1053  }
1054  if (!success)
1055    m_addr = LLDB_INVALID_ADDRESS;
1056  return success;
1057}
1058
1059bool EmulateInstructionMIPS::EvaluateInstruction(uint32_t evaluate_options) {
1060  bool success = false;
1061  llvm::MCInst mc_insn;
1062  uint64_t insn_size;
1063  DataExtractor data;
1064
1065  /* Keep the complexity of the decode logic with the llvm::MCDisassembler
1066   * class. */
1067  if (m_opcode.GetData(data)) {
1068    llvm::MCDisassembler::DecodeStatus decode_status;
1069    llvm::ArrayRef<uint8_t> raw_insn(data.GetDataStart(), data.GetByteSize());
1070    if (m_use_alt_disaasm)
1071      decode_status = m_alt_disasm->getInstruction(mc_insn, insn_size, raw_insn,
1072                                                   m_addr, llvm::nulls());
1073    else
1074      decode_status = m_disasm->getInstruction(mc_insn, insn_size, raw_insn,
1075                                               m_addr, llvm::nulls());
1076
1077    if (decode_status != llvm::MCDisassembler::Success)
1078      return false;
1079  }
1080
1081  /*
1082   * mc_insn.getOpcode() returns decoded opcode. However to make use
1083   * of llvm::Mips::<insn> we would need "MipsGenInstrInfo.inc".
1084  */
1085  const char *op_name = m_insn_info->getName(mc_insn.getOpcode()).data();
1086
1087  if (op_name == nullptr)
1088    return false;
1089
1090  /*
1091   * Decoding has been done already. Just get the call-back function
1092   * and emulate the instruction.
1093  */
1094  MipsOpcode *opcode_data = GetOpcodeForInstruction(op_name);
1095
1096  if (opcode_data == nullptr)
1097    return false;
1098
1099  uint64_t old_pc = 0, new_pc = 0;
1100  const bool auto_advance_pc =
1101      evaluate_options & eEmulateInstructionOptionAutoAdvancePC;
1102
1103  if (auto_advance_pc) {
1104    old_pc =
1105        ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
1106    if (!success)
1107      return false;
1108  }
1109
1110  /* emulate instruction */
1111  success = (this->*opcode_data->callback)(mc_insn);
1112  if (!success)
1113    return false;
1114
1115  if (auto_advance_pc) {
1116    new_pc =
1117        ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
1118    if (!success)
1119      return false;
1120
1121    /* If we haven't changed the PC, change it here */
1122    if (old_pc == new_pc) {
1123      new_pc += 4;
1124      Context context;
1125      if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
1126                                 new_pc))
1127        return false;
1128    }
1129  }
1130
1131  return true;
1132}
1133
1134bool EmulateInstructionMIPS::CreateFunctionEntryUnwind(
1135    UnwindPlan &unwind_plan) {
1136  unwind_plan.Clear();
1137  unwind_plan.SetRegisterKind(eRegisterKindDWARF);
1138
1139  UnwindPlan::RowSP row(new UnwindPlan::Row);
1140  const bool can_replace = false;
1141
1142  // Our previous Call Frame Address is the stack pointer
1143  row->GetCFAValue().SetIsRegisterPlusOffset(dwarf_sp_mips, 0);
1144
1145  // Our previous PC is in the RA
1146  row->SetRegisterLocationToRegister(dwarf_pc_mips, dwarf_ra_mips, can_replace);
1147
1148  unwind_plan.AppendRow(row);
1149
1150  // All other registers are the same.
1151  unwind_plan.SetSourceName("EmulateInstructionMIPS");
1152  unwind_plan.SetSourcedFromCompiler(eLazyBoolNo);
1153  unwind_plan.SetUnwindPlanValidAtAllInstructions(eLazyBoolYes);
1154  unwind_plan.SetUnwindPlanForSignalTrap(eLazyBoolNo);
1155  unwind_plan.SetReturnAddressRegister(dwarf_ra_mips);
1156
1157  return true;
1158}
1159
1160bool EmulateInstructionMIPS::nonvolatile_reg_p(uint32_t regnum) {
1161  switch (regnum) {
1162  case dwarf_r16_mips:
1163  case dwarf_r17_mips:
1164  case dwarf_r18_mips:
1165  case dwarf_r19_mips:
1166  case dwarf_r20_mips:
1167  case dwarf_r21_mips:
1168  case dwarf_r22_mips:
1169  case dwarf_r23_mips:
1170  case dwarf_gp_mips:
1171  case dwarf_sp_mips:
1172  case dwarf_r30_mips:
1173  case dwarf_ra_mips:
1174    return true;
1175  default:
1176    return false;
1177  }
1178  return false;
1179}
1180
1181bool EmulateInstructionMIPS::Emulate_ADDiu(llvm::MCInst &insn) {
1182  // ADDIU rt, rs, immediate
1183  // GPR[rt] <- GPR[rs] + sign_extend(immediate)
1184
1185  uint8_t dst, src;
1186  bool success = false;
1187  const uint32_t imm16 = insn.getOperand(2).getImm();
1188  int64_t imm = SignedBits(imm16, 15, 0);
1189
1190  dst = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
1191  src = m_reg_info->getEncodingValue(insn.getOperand(1).getReg());
1192
1193  // If immediate value is greater then 2^16 - 1 then clang generate LUI,
1194  // ADDIU, SUBU instructions in prolog. Example lui    $1, 0x2 addiu $1, $1,
1195  // -0x5920 subu  $sp, $sp, $1 In this case, ADDIU dst and src will be same
1196  // and not equal to sp
1197  if (dst == src) {
1198    Context context;
1199
1200    /* read <src> register */
1201    const int64_t src_opd_val = ReadRegisterUnsigned(
1202        eRegisterKindDWARF, dwarf_zero_mips + src, 0, &success);
1203    if (!success)
1204      return false;
1205
1206    /* Check if this is daddiu sp, sp, imm16 */
1207    if (dst == dwarf_sp_mips) {
1208      uint64_t result = src_opd_val + imm;
1209      RegisterInfo reg_info_sp;
1210
1211      if (GetRegisterInfo(eRegisterKindDWARF, dwarf_sp_mips, reg_info_sp))
1212        context.SetRegisterPlusOffset(reg_info_sp, imm);
1213
1214      /* We are allocating bytes on stack */
1215      context.type = eContextAdjustStackPointer;
1216
1217      WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_sp_mips, result);
1218      return true;
1219    }
1220
1221    imm += src_opd_val;
1222    context.SetImmediateSigned(imm);
1223    context.type = eContextImmediate;
1224
1225    if (!WriteRegisterUnsigned(context, eRegisterKindDWARF,
1226                               dwarf_zero_mips + dst, imm))
1227      return false;
1228  }
1229
1230  return true;
1231}
1232
1233bool EmulateInstructionMIPS::Emulate_SW(llvm::MCInst &insn) {
1234  bool success = false;
1235  uint32_t imm16 = insn.getOperand(2).getImm();
1236  uint32_t imm = SignedBits(imm16, 15, 0);
1237  uint32_t src, base;
1238  int32_t address;
1239  Context bad_vaddr_context;
1240
1241  RegisterInfo reg_info_base;
1242
1243  src = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
1244  base = m_reg_info->getEncodingValue(insn.getOperand(1).getReg());
1245
1246  if (!GetRegisterInfo(eRegisterKindDWARF, dwarf_zero_mips + base,
1247                       reg_info_base))
1248    return false;
1249
1250  /* read base register */
1251  address = (int32_t)ReadRegisterUnsigned(eRegisterKindDWARF,
1252                                          dwarf_zero_mips + base, 0, &success);
1253  if (!success)
1254    return false;
1255
1256  /* destination address */
1257  address = address + imm;
1258
1259  /* Set the bad_vaddr register with base address used in the instruction */
1260  bad_vaddr_context.type = eContextInvalid;
1261  WriteRegisterUnsigned(bad_vaddr_context, eRegisterKindDWARF, dwarf_bad_mips,
1262                        address);
1263
1264  /* We look for sp based non-volatile register stores */
1265  if (nonvolatile_reg_p(src)) {
1266
1267    RegisterInfo reg_info_src;
1268
1269    if (!GetRegisterInfo(eRegisterKindDWARF, dwarf_zero_mips + src,
1270                         reg_info_src))
1271      return false;
1272
1273    Context context;
1274    RegisterValue data_src;
1275    context.type = eContextPushRegisterOnStack;
1276    context.SetRegisterToRegisterPlusOffset(reg_info_src, reg_info_base, 0);
1277
1278    uint8_t buffer[RegisterValue::kMaxRegisterByteSize];
1279    Status error;
1280
1281    if (!ReadRegister(&reg_info_base, data_src))
1282      return false;
1283
1284    if (data_src.GetAsMemoryData(&reg_info_src, buffer, reg_info_src.byte_size,
1285                                 eByteOrderLittle, error) == 0)
1286      return false;
1287
1288    if (!WriteMemory(context, address, buffer, reg_info_src.byte_size))
1289      return false;
1290
1291    return true;
1292  }
1293
1294  return false;
1295}
1296
1297bool EmulateInstructionMIPS::Emulate_LW(llvm::MCInst &insn) {
1298  bool success = false;
1299  uint32_t src, base;
1300  int32_t imm, address;
1301  Context bad_vaddr_context;
1302
1303  src = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
1304  base = m_reg_info->getEncodingValue(insn.getOperand(1).getReg());
1305  imm = insn.getOperand(2).getImm();
1306
1307  RegisterInfo reg_info_base;
1308  if (!GetRegisterInfo(eRegisterKindDWARF, dwarf_zero_mips + base,
1309                       reg_info_base))
1310    return false;
1311
1312  /* read base register */
1313  address = (int32_t)ReadRegisterUnsigned(eRegisterKindDWARF,
1314                                          dwarf_zero_mips + base, 0, &success);
1315  if (!success)
1316    return false;
1317
1318  /* destination address */
1319  address = address + imm;
1320
1321  /* Set the bad_vaddr register with base address used in the instruction */
1322  bad_vaddr_context.type = eContextInvalid;
1323  WriteRegisterUnsigned(bad_vaddr_context, eRegisterKindDWARF, dwarf_bad_mips,
1324                        address);
1325
1326  if (nonvolatile_reg_p(src)) {
1327    RegisterValue data_src;
1328    RegisterInfo reg_info_src;
1329
1330    if (!GetRegisterInfo(eRegisterKindDWARF, dwarf_zero_mips + src,
1331                         reg_info_src))
1332      return false;
1333
1334    Context context;
1335    context.type = eContextPopRegisterOffStack;
1336    context.SetAddress(address);
1337
1338    return WriteRegister(context, &reg_info_src, data_src);
1339  }
1340
1341  return false;
1342}
1343
1344bool EmulateInstructionMIPS::Emulate_SUBU_ADDU(llvm::MCInst &insn) {
1345  // SUBU sp, <src>, <rt>
1346  // ADDU sp, <src>, <rt>
1347  // ADDU dst, sp, <rt>
1348
1349  bool success = false;
1350  uint64_t result;
1351  uint8_t src, dst, rt;
1352  const char *op_name = m_insn_info->getName(insn.getOpcode()).data();
1353
1354  dst = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
1355  src = m_reg_info->getEncodingValue(insn.getOperand(1).getReg());
1356
1357  /* Check if sp is destination register */
1358  if (dst == dwarf_sp_mips) {
1359    rt = m_reg_info->getEncodingValue(insn.getOperand(2).getReg());
1360
1361    /* read <src> register */
1362    uint64_t src_opd_val = ReadRegisterUnsigned(
1363        eRegisterKindDWARF, dwarf_zero_mips + src, 0, &success);
1364    if (!success)
1365      return false;
1366
1367    /* read <rt > register */
1368    uint64_t rt_opd_val = ReadRegisterUnsigned(
1369        eRegisterKindDWARF, dwarf_zero_mips + rt, 0, &success);
1370    if (!success)
1371      return false;
1372
1373    if (!strcasecmp(op_name, "SUBU"))
1374      result = src_opd_val - rt_opd_val;
1375    else
1376      result = src_opd_val + rt_opd_val;
1377
1378    Context context;
1379    RegisterInfo reg_info_sp;
1380    if (GetRegisterInfo(eRegisterKindDWARF, dwarf_sp_mips, reg_info_sp))
1381      context.SetRegisterPlusOffset(reg_info_sp, rt_opd_val);
1382
1383    /* We are allocating bytes on stack */
1384    context.type = eContextAdjustStackPointer;
1385
1386    WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_sp_mips, result);
1387
1388    return true;
1389  } else if (src == dwarf_sp_mips) {
1390    rt = m_reg_info->getEncodingValue(insn.getOperand(2).getReg());
1391
1392    /* read <src> register */
1393    uint64_t src_opd_val = ReadRegisterUnsigned(
1394        eRegisterKindDWARF, dwarf_zero_mips + src, 0, &success);
1395    if (!success)
1396      return false;
1397
1398    /* read <rt> register */
1399    uint64_t rt_opd_val = ReadRegisterUnsigned(
1400        eRegisterKindDWARF, dwarf_zero_mips + rt, 0, &success);
1401    if (!success)
1402      return false;
1403
1404    Context context;
1405
1406    if (!strcasecmp(op_name, "SUBU"))
1407      result = src_opd_val - rt_opd_val;
1408    else
1409      result = src_opd_val + rt_opd_val;
1410
1411    context.SetImmediateSigned(result);
1412    context.type = eContextImmediate;
1413
1414    if (!WriteRegisterUnsigned(context, eRegisterKindDWARF,
1415                               dwarf_zero_mips + dst, result))
1416      return false;
1417  }
1418
1419  return true;
1420}
1421
1422bool EmulateInstructionMIPS::Emulate_LUI(llvm::MCInst &insn) {
1423  // LUI rt, immediate
1424  // GPR[rt] <- sign_extend(immediate << 16)
1425
1426  const uint32_t imm32 = insn.getOperand(1).getImm() << 16;
1427  int64_t imm = SignedBits(imm32, 31, 0);
1428  uint8_t rt;
1429  Context context;
1430
1431  rt = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
1432  context.SetImmediateSigned(imm);
1433  context.type = eContextImmediate;
1434
1435  return WriteRegisterUnsigned(context, eRegisterKindDWARF,
1436                               dwarf_zero_mips + rt, imm);
1437}
1438
1439bool EmulateInstructionMIPS::Emulate_ADDIUSP(llvm::MCInst &insn) {
1440  bool success = false;
1441  const uint32_t imm9 = insn.getOperand(0).getImm();
1442  uint64_t result;
1443
1444  // This instruction operates implicitly on stack pointer, so read <sp>
1445  // register.
1446  uint64_t src_opd_val =
1447      ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_sp_mips, 0, &success);
1448  if (!success)
1449    return false;
1450
1451  result = src_opd_val + imm9;
1452
1453  Context context;
1454  RegisterInfo reg_info_sp;
1455  if (GetRegisterInfo(eRegisterKindDWARF, dwarf_sp_mips, reg_info_sp))
1456    context.SetRegisterPlusOffset(reg_info_sp, imm9);
1457
1458  // We are adjusting the stack.
1459  context.type = eContextAdjustStackPointer;
1460
1461  WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_sp_mips, result);
1462  return true;
1463}
1464
1465bool EmulateInstructionMIPS::Emulate_ADDIUS5(llvm::MCInst &insn) {
1466  bool success = false;
1467  uint32_t base;
1468  const uint32_t imm4 = insn.getOperand(2).getImm();
1469  uint64_t result;
1470
1471  // The source and destination register is same for this instruction.
1472  base = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
1473
1474  // We are looking for stack adjustment only
1475  if (base == dwarf_sp_mips) {
1476    // Read stack pointer register
1477    uint64_t src_opd_val = ReadRegisterUnsigned(
1478        eRegisterKindDWARF, dwarf_zero_mips + base, 0, &success);
1479    if (!success)
1480      return false;
1481
1482    result = src_opd_val + imm4;
1483
1484    Context context;
1485    RegisterInfo reg_info_sp;
1486    if (GetRegisterInfo(eRegisterKindDWARF, dwarf_sp_mips, reg_info_sp))
1487      context.SetRegisterPlusOffset(reg_info_sp, imm4);
1488
1489    // We are adjusting the stack.
1490    context.type = eContextAdjustStackPointer;
1491
1492    WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_sp_mips, result);
1493  }
1494
1495  return true;
1496}
1497
1498bool EmulateInstructionMIPS::Emulate_SWSP(llvm::MCInst &insn) {
1499  bool success = false;
1500  uint32_t imm5 = insn.getOperand(2).getImm();
1501  uint32_t src, base;
1502  Context bad_vaddr_context;
1503  uint32_t address;
1504
1505  src = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
1506  base = m_reg_info->getEncodingValue(insn.getOperand(1).getReg());
1507
1508  RegisterInfo reg_info_base;
1509
1510  if (!GetRegisterInfo(eRegisterKindDWARF, dwarf_zero_mips + base,
1511                       reg_info_base))
1512    return false;
1513
1514  // read base register
1515  address = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_zero_mips + base, 0,
1516                                 &success);
1517  if (!success)
1518    return false;
1519
1520  // destination address
1521  address = address + imm5;
1522
1523  // We use bad_vaddr_context to store base address which is used by H/W
1524  // watchpoint Set the bad_vaddr register with base address used in the
1525  // instruction
1526  bad_vaddr_context.type = eContextInvalid;
1527  WriteRegisterUnsigned(bad_vaddr_context, eRegisterKindDWARF, dwarf_bad_mips,
1528                        address);
1529
1530  // We look for sp based non-volatile register stores.
1531  if (base == dwarf_sp_mips && nonvolatile_reg_p(src)) {
1532    RegisterInfo reg_info_src = {};
1533    Context context;
1534    RegisterValue data_src;
1535    context.type = eContextPushRegisterOnStack;
1536    context.SetRegisterToRegisterPlusOffset(reg_info_src, reg_info_base, 0);
1537
1538    uint8_t buffer[RegisterValue::kMaxRegisterByteSize];
1539    Status error;
1540
1541    if (!ReadRegister(&reg_info_base, data_src))
1542      return false;
1543
1544    if (data_src.GetAsMemoryData(&reg_info_src, buffer, reg_info_src.byte_size,
1545                                 eByteOrderLittle, error) == 0)
1546      return false;
1547
1548    if (!WriteMemory(context, address, buffer, reg_info_src.byte_size))
1549      return false;
1550
1551    return true;
1552  }
1553
1554  return false;
1555}
1556
1557/* Emulate SWM16,SWM32 and SWP instruction.
1558
1559   SWM16 always has stack pointer as a base register (but it is still available
1560   in MCInst as an operand).
1561   SWM32 and SWP can have base register other than stack pointer.
1562*/
1563bool EmulateInstructionMIPS::Emulate_SWM16_32(llvm::MCInst &insn) {
1564  bool success = false;
1565  uint32_t src, base;
1566  uint32_t num_operands = insn.getNumOperands(); // No of operands vary based on
1567                                                 // no of regs to store.
1568
1569  // Base register is second last operand of the instruction.
1570  base =
1571      m_reg_info->getEncodingValue(insn.getOperand(num_operands - 2).getReg());
1572
1573  // We are looking for sp based stores so if base is not a stack pointer then
1574  // don't proceed.
1575  if (base != dwarf_sp_mips)
1576    return false;
1577
1578  // offset is always the last operand.
1579  uint32_t offset = insn.getOperand(num_operands - 1).getImm();
1580
1581  RegisterInfo reg_info_base;
1582  RegisterInfo reg_info_src;
1583
1584  if (!GetRegisterInfo(eRegisterKindDWARF, dwarf_zero_mips + base,
1585                       reg_info_base))
1586    return false;
1587
1588  // read SP
1589  uint32_t base_address = ReadRegisterUnsigned(
1590      eRegisterKindDWARF, dwarf_zero_mips + base, 0, &success);
1591  if (!success)
1592    return false;
1593
1594  // Resulting base addrss
1595  base_address = base_address + offset;
1596
1597  // Total no of registers to be stored are num_operands-2.
1598  for (uint32_t i = 0; i < num_operands - 2; i++) {
1599    // Get the register number to be stored.
1600    src = m_reg_info->getEncodingValue(insn.getOperand(i).getReg());
1601
1602    /*
1603        Record only non-volatile stores.
1604        This check is required for SWP instruction because source operand could
1605       be any register.
1606        SWM16 and SWM32 instruction always has saved registers as source
1607       operands.
1608    */
1609    if (!nonvolatile_reg_p(src))
1610      return false;
1611
1612    if (!GetRegisterInfo(eRegisterKindDWARF, dwarf_zero_mips + src,
1613                         reg_info_src))
1614      return false;
1615
1616    Context context;
1617    RegisterValue data_src;
1618    context.type = eContextPushRegisterOnStack;
1619    context.SetRegisterToRegisterPlusOffset(reg_info_src, reg_info_base, 0);
1620
1621    uint8_t buffer[RegisterValue::kMaxRegisterByteSize];
1622    Status error;
1623
1624    if (!ReadRegister(&reg_info_base, data_src))
1625      return false;
1626
1627    if (data_src.GetAsMemoryData(&reg_info_src, buffer, reg_info_src.byte_size,
1628                                 eByteOrderLittle, error) == 0)
1629      return false;
1630
1631    if (!WriteMemory(context, base_address, buffer, reg_info_src.byte_size))
1632      return false;
1633
1634    // Stack address for next register
1635    base_address = base_address + reg_info_src.byte_size;
1636  }
1637  return true;
1638}
1639
1640bool EmulateInstructionMIPS::Emulate_LWSP(llvm::MCInst &insn) {
1641  bool success = false;
1642  uint32_t src = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
1643  uint32_t base = m_reg_info->getEncodingValue(insn.getOperand(1).getReg());
1644  uint32_t imm5 = insn.getOperand(2).getImm();
1645  Context bad_vaddr_context;
1646
1647  RegisterInfo reg_info_base;
1648  if (!GetRegisterInfo(eRegisterKindDWARF, dwarf_zero_mips + base,
1649                       reg_info_base))
1650    return false;
1651
1652  // read base register
1653  uint32_t base_address = ReadRegisterUnsigned(
1654      eRegisterKindDWARF, dwarf_zero_mips + base, 0, &success);
1655  if (!success)
1656    return false;
1657
1658  base_address = base_address + imm5;
1659
1660  // We use bad_vaddr_context to store base address which is used by H/W
1661  // watchpoint Set the bad_vaddr register with base address used in the
1662  // instruction
1663  bad_vaddr_context.type = eContextInvalid;
1664  WriteRegisterUnsigned(bad_vaddr_context, eRegisterKindDWARF, dwarf_bad_mips,
1665                        base_address);
1666
1667  if (base == dwarf_sp_mips && nonvolatile_reg_p(src)) {
1668    RegisterValue data_src;
1669    RegisterInfo reg_info_src;
1670
1671    if (!GetRegisterInfo(eRegisterKindDWARF, dwarf_zero_mips + src,
1672                         reg_info_src))
1673      return false;
1674
1675    Context context;
1676    context.type = eContextPopRegisterOffStack;
1677    context.SetAddress(base_address);
1678
1679    return WriteRegister(context, &reg_info_src, data_src);
1680  }
1681
1682  return false;
1683}
1684
1685/* Emulate LWM16, LWM32 and LWP instructions.
1686
1687   LWM16 always has stack pointer as a base register (but it is still available
1688   in MCInst as an operand).
1689   LWM32 and LWP can have base register other than stack pointer.
1690*/
1691bool EmulateInstructionMIPS::Emulate_LWM16_32(llvm::MCInst &insn) {
1692  bool success = false;
1693  uint32_t dst, base;
1694  uint32_t num_operands = insn.getNumOperands(); // No of operands vary based on
1695                                                 // no of regs to store.
1696  uint32_t imm = insn.getOperand(num_operands - 1)
1697                     .getImm(); // imm is the last operand in the instruction.
1698
1699  // Base register is second last operand of the instruction.
1700  base =
1701      m_reg_info->getEncodingValue(insn.getOperand(num_operands - 2).getReg());
1702
1703  // We are looking for sp based loads so if base is not a stack pointer then
1704  // don't proceed.
1705  if (base != dwarf_sp_mips)
1706    return false;
1707
1708  uint32_t base_address = ReadRegisterUnsigned(
1709      eRegisterKindDWARF, dwarf_zero_mips + base, 0, &success);
1710  if (!success)
1711    return false;
1712
1713  base_address = base_address + imm;
1714
1715  RegisterValue data_dst;
1716  RegisterInfo reg_info_dst;
1717
1718  // Total no of registers to be re-stored are num_operands-2.
1719  for (uint32_t i = 0; i < num_operands - 2; i++) {
1720    // Get the register number to be re-stored.
1721    dst = m_reg_info->getEncodingValue(insn.getOperand(i).getReg());
1722
1723    /*
1724        Record only non-volatile loads.
1725        This check is required for LWP instruction because destination operand
1726       could be any register.
1727        LWM16 and LWM32 instruction always has saved registers as destination
1728       operands.
1729    */
1730    if (!nonvolatile_reg_p(dst))
1731      return false;
1732
1733    if (!GetRegisterInfo(eRegisterKindDWARF, dwarf_zero_mips + dst,
1734                         reg_info_dst))
1735      return false;
1736
1737    Context context;
1738    context.type = eContextPopRegisterOffStack;
1739    context.SetAddress(base_address + (i * 4));
1740
1741    if (!WriteRegister(context, &reg_info_dst, data_dst))
1742      return false;
1743  }
1744
1745  return true;
1746}
1747
1748bool EmulateInstructionMIPS::Emulate_JRADDIUSP(llvm::MCInst &insn) {
1749  bool success = false;
1750  int32_t imm5 = insn.getOperand(0).getImm();
1751
1752  /* JRADDIUSP immediate
1753  *       PC <- RA
1754  *       SP <- SP + zero_extend(Immediate << 2)
1755  */
1756
1757  // This instruction operates implicitly on stack pointer, so read <sp>
1758  // register.
1759  int32_t src_opd_val =
1760      ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_sp_mips, 0, &success);
1761  if (!success)
1762    return false;
1763
1764  int32_t ra_val =
1765      ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_ra_mips, 0, &success);
1766  if (!success)
1767    return false;
1768
1769  int32_t result = src_opd_val + imm5;
1770
1771  Context context;
1772
1773  // Update the PC
1774  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
1775                             ra_val))
1776    return false;
1777
1778  RegisterInfo reg_info_sp;
1779  if (GetRegisterInfo(eRegisterKindDWARF, dwarf_sp_mips, reg_info_sp))
1780    context.SetRegisterPlusOffset(reg_info_sp, imm5);
1781
1782  // We are adjusting stack
1783  context.type = eContextAdjustStackPointer;
1784
1785  // update SP
1786  return WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_sp_mips,
1787                               result);
1788}
1789
1790static int IsAdd64bitOverflow(int32_t a, int32_t b) {
1791  int32_t r = (uint32_t)a + (uint32_t)b;
1792  return (a < 0 && b < 0 && r >= 0) || (a >= 0 && b >= 0 && r < 0);
1793}
1794
1795/*
1796    Emulate below MIPS branch instructions.
1797    BEQ, BNE : Branch on condition
1798    BEQL, BNEL : Branch likely
1799*/
1800bool EmulateInstructionMIPS::Emulate_BXX_3ops(llvm::MCInst &insn) {
1801  bool success = false;
1802  uint32_t rs, rt;
1803  int32_t offset, pc, target = 0, rs_val, rt_val;
1804  const char *op_name = m_insn_info->getName(insn.getOpcode()).data();
1805
1806  rs = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
1807  rt = m_reg_info->getEncodingValue(insn.getOperand(1).getReg());
1808  offset = insn.getOperand(2).getImm();
1809
1810  pc = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
1811  if (!success)
1812    return false;
1813
1814  rs_val = (int32_t)ReadRegisterUnsigned(eRegisterKindDWARF,
1815                                         dwarf_zero_mips + rs, 0, &success);
1816  if (!success)
1817    return false;
1818
1819  rt_val = (int32_t)ReadRegisterUnsigned(eRegisterKindDWARF,
1820                                         dwarf_zero_mips + rt, 0, &success);
1821  if (!success)
1822    return false;
1823
1824  if (!strcasecmp(op_name, "BEQ") || !strcasecmp(op_name, "BEQL")) {
1825    if (rs_val == rt_val)
1826      target = pc + offset;
1827    else
1828      target = pc + 8;
1829  } else if (!strcasecmp(op_name, "BNE") || !strcasecmp(op_name, "BNEL")) {
1830    if (rs_val != rt_val)
1831      target = pc + offset;
1832    else
1833      target = pc + 8;
1834  }
1835
1836  Context context;
1837  context.type = eContextRelativeBranchImmediate;
1838  context.SetImmediate(offset);
1839
1840  return WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
1841                               target);
1842}
1843
1844/*
1845    Emulate below MIPS branch instructions.
1846    BEQC, BNEC, BLTC, BGEC, BLTUC, BGEUC, BOVC, BNVC: Compact branch
1847   instructions with no delay slot
1848*/
1849bool EmulateInstructionMIPS::Emulate_BXX_3ops_C(llvm::MCInst &insn) {
1850  bool success = false;
1851  uint32_t rs, rt;
1852  int32_t offset, pc, target = 0, rs_val, rt_val;
1853  const char *op_name = m_insn_info->getName(insn.getOpcode()).data();
1854  uint32_t current_inst_size = m_insn_info->get(insn.getOpcode()).getSize();
1855
1856  rs = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
1857  rt = m_reg_info->getEncodingValue(insn.getOperand(1).getReg());
1858  offset = insn.getOperand(2).getImm();
1859
1860  pc = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
1861  if (!success)
1862    return false;
1863
1864  rs_val = (int32_t)ReadRegisterUnsigned(eRegisterKindDWARF,
1865                                         dwarf_zero_mips + rs, 0, &success);
1866  if (!success)
1867    return false;
1868
1869  rt_val = (int32_t)ReadRegisterUnsigned(eRegisterKindDWARF,
1870                                         dwarf_zero_mips + rt, 0, &success);
1871  if (!success)
1872    return false;
1873
1874  if (!strcasecmp(op_name, "BEQC")) {
1875    if (rs_val == rt_val)
1876      target = pc + offset;
1877    else
1878      target = pc + 4;
1879  } else if (!strcasecmp(op_name, "BNEC")) {
1880    if (rs_val != rt_val)
1881      target = pc + offset;
1882    else
1883      target = pc + 4;
1884  } else if (!strcasecmp(op_name, "BLTC")) {
1885    if (rs_val < rt_val)
1886      target = pc + offset;
1887    else
1888      target = pc + 4;
1889  } else if (!strcasecmp(op_name, "BGEC")) {
1890    if (rs_val >= rt_val)
1891      target = pc + offset;
1892    else
1893      target = pc + 4;
1894  } else if (!strcasecmp(op_name, "BLTUC")) {
1895    if (rs_val < rt_val)
1896      target = pc + offset;
1897    else
1898      target = pc + 4;
1899  } else if (!strcasecmp(op_name, "BGEUC")) {
1900    if ((uint32_t)rs_val >= (uint32_t)rt_val)
1901      target = pc + offset;
1902    else
1903      target = pc + 4;
1904  } else if (!strcasecmp(op_name, "BOVC")) {
1905    if (IsAdd64bitOverflow(rs_val, rt_val))
1906      target = pc + offset;
1907    else
1908      target = pc + 4;
1909  } else if (!strcasecmp(op_name, "BNVC")) {
1910    if (!IsAdd64bitOverflow(rs_val, rt_val))
1911      target = pc + offset;
1912    else
1913      target = pc + 4;
1914  }
1915
1916  Context context;
1917  context.type = eContextRelativeBranchImmediate;
1918  context.SetImmediate(current_inst_size + offset);
1919
1920  return WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
1921                               target);
1922}
1923
1924/*
1925    Emulate below MIPS conditional branch and link instructions.
1926    BLEZALC, BGEZALC, BLTZALC, BGTZALC, BEQZALC, BNEZALC : Compact branches
1927*/
1928bool EmulateInstructionMIPS::Emulate_Bcond_Link_C(llvm::MCInst &insn) {
1929  bool success = false;
1930  uint32_t rs;
1931  int32_t offset, pc, target = 0;
1932  int32_t rs_val;
1933  const char *op_name = m_insn_info->getName(insn.getOpcode()).data();
1934
1935  rs = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
1936  offset = insn.getOperand(1).getImm();
1937
1938  pc = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
1939  if (!success)
1940    return false;
1941
1942  rs_val = (int32_t)ReadRegisterUnsigned(eRegisterKindDWARF,
1943                                         dwarf_zero_mips + rs, 0, &success);
1944  if (!success)
1945    return false;
1946
1947  if (!strcasecmp(op_name, "BLEZALC")) {
1948    if (rs_val <= 0)
1949      target = pc + offset;
1950    else
1951      target = pc + 4;
1952  } else if (!strcasecmp(op_name, "BGEZALC")) {
1953    if (rs_val >= 0)
1954      target = pc + offset;
1955    else
1956      target = pc + 4;
1957  } else if (!strcasecmp(op_name, "BLTZALC")) {
1958    if (rs_val < 0)
1959      target = pc + offset;
1960    else
1961      target = pc + 4;
1962  } else if (!strcasecmp(op_name, "BGTZALC")) {
1963    if (rs_val > 0)
1964      target = pc + offset;
1965    else
1966      target = pc + 4;
1967  } else if (!strcasecmp(op_name, "BEQZALC")) {
1968    if (rs_val == 0)
1969      target = pc + offset;
1970    else
1971      target = pc + 4;
1972  } else if (!strcasecmp(op_name, "BNEZALC")) {
1973    if (rs_val != 0)
1974      target = pc + offset;
1975    else
1976      target = pc + 4;
1977  }
1978
1979  Context context;
1980
1981  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
1982                             target))
1983    return false;
1984
1985  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_ra_mips,
1986                             pc + 4))
1987    return false;
1988
1989  return true;
1990}
1991
1992/*
1993    Emulate below MIPS Non-Compact conditional branch and link instructions.
1994    BLTZAL, BGEZAL      :
1995    BLTZALL, BGEZALL    : Branch likely
1996*/
1997bool EmulateInstructionMIPS::Emulate_Bcond_Link(llvm::MCInst &insn) {
1998  bool success = false;
1999  uint32_t rs;
2000  int32_t offset, pc, target = 0;
2001  int32_t rs_val;
2002  const char *op_name = m_insn_info->getName(insn.getOpcode()).data();
2003
2004  rs = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
2005  offset = insn.getOperand(1).getImm();
2006
2007  pc = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
2008  if (!success)
2009    return false;
2010
2011  rs_val = (int32_t)ReadRegisterUnsigned(eRegisterKindDWARF,
2012                                         dwarf_zero_mips + rs, 0, &success);
2013  if (!success)
2014    return false;
2015
2016  if (!strcasecmp(op_name, "BLTZAL") || !strcasecmp(op_name, "BLTZALL")) {
2017    if ((int32_t)rs_val < 0)
2018      target = pc + offset;
2019    else
2020      target = pc + 8;
2021  } else if (!strcasecmp(op_name, "BGEZAL") ||
2022             !strcasecmp(op_name, "BGEZALL")) {
2023    if ((int32_t)rs_val >= 0)
2024      target = pc + offset;
2025    else
2026      target = pc + 8;
2027  }
2028
2029  Context context;
2030
2031  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2032                             target))
2033    return false;
2034
2035  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_ra_mips,
2036                             pc + 8))
2037    return false;
2038
2039  return true;
2040}
2041
2042/*
2043    Emulate below MIPS branch instructions.
2044    BLTZL, BGEZL, BGTZL, BLEZL : Branch likely
2045    BLTZ, BGEZ, BGTZ, BLEZ     : Non-compact branches
2046*/
2047bool EmulateInstructionMIPS::Emulate_BXX_2ops(llvm::MCInst &insn) {
2048  bool success = false;
2049  uint32_t rs;
2050  int32_t offset, pc, target = 0;
2051  int32_t rs_val;
2052  const char *op_name = m_insn_info->getName(insn.getOpcode()).data();
2053
2054  rs = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
2055  offset = insn.getOperand(1).getImm();
2056
2057  pc = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
2058  if (!success)
2059    return false;
2060
2061  rs_val = (int32_t)ReadRegisterUnsigned(eRegisterKindDWARF,
2062                                         dwarf_zero_mips + rs, 0, &success);
2063  if (!success)
2064    return false;
2065
2066  if (!strcasecmp(op_name, "BLTZL") || !strcasecmp(op_name, "BLTZ")) {
2067    if (rs_val < 0)
2068      target = pc + offset;
2069    else
2070      target = pc + 8;
2071  } else if (!strcasecmp(op_name, "BGEZL") || !strcasecmp(op_name, "BGEZ")) {
2072    if (rs_val >= 0)
2073      target = pc + offset;
2074    else
2075      target = pc + 8;
2076  } else if (!strcasecmp(op_name, "BGTZL") || !strcasecmp(op_name, "BGTZ")) {
2077    if (rs_val > 0)
2078      target = pc + offset;
2079    else
2080      target = pc + 8;
2081  } else if (!strcasecmp(op_name, "BLEZL") || !strcasecmp(op_name, "BLEZ")) {
2082    if (rs_val <= 0)
2083      target = pc + offset;
2084    else
2085      target = pc + 8;
2086  }
2087
2088  Context context;
2089  context.type = eContextRelativeBranchImmediate;
2090  context.SetImmediate(offset);
2091
2092  return WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2093                               target);
2094}
2095
2096/*
2097    Emulate below MIPS branch instructions.
2098    BLTZC, BLEZC, BGEZC, BGTZC, BEQZC, BNEZC : Compact Branches
2099*/
2100bool EmulateInstructionMIPS::Emulate_BXX_2ops_C(llvm::MCInst &insn) {
2101  bool success = false;
2102  uint32_t rs;
2103  int32_t offset, pc, target = 0;
2104  int32_t rs_val;
2105  const char *op_name = m_insn_info->getName(insn.getOpcode()).data();
2106  uint32_t current_inst_size = m_insn_info->get(insn.getOpcode()).getSize();
2107
2108  rs = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
2109  offset = insn.getOperand(1).getImm();
2110
2111  pc = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
2112  if (!success)
2113    return false;
2114
2115  rs_val = (int32_t)ReadRegisterUnsigned(eRegisterKindDWARF,
2116                                         dwarf_zero_mips + rs, 0, &success);
2117  if (!success)
2118    return false;
2119
2120  if (!strcasecmp(op_name, "BLTZC")) {
2121    if (rs_val < 0)
2122      target = pc + offset;
2123    else
2124      target = pc + 4;
2125  } else if (!strcasecmp(op_name, "BLEZC")) {
2126    if (rs_val <= 0)
2127      target = pc + offset;
2128    else
2129      target = pc + 4;
2130  } else if (!strcasecmp(op_name, "BGEZC")) {
2131    if (rs_val >= 0)
2132      target = pc + offset;
2133    else
2134      target = pc + 4;
2135  } else if (!strcasecmp(op_name, "BGTZC")) {
2136    if (rs_val > 0)
2137      target = pc + offset;
2138    else
2139      target = pc + 4;
2140  } else if (!strcasecmp(op_name, "BEQZC")) {
2141    if (rs_val == 0)
2142      target = pc + offset;
2143    else
2144      target = pc + 4;
2145  } else if (!strcasecmp(op_name, "BNEZC")) {
2146    if (rs_val != 0)
2147      target = pc + offset;
2148    else
2149      target = pc + 4;
2150  }
2151
2152  Context context;
2153  context.type = eContextRelativeBranchImmediate;
2154  context.SetImmediate(current_inst_size + offset);
2155
2156  return WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2157                               target);
2158}
2159
2160bool EmulateInstructionMIPS::Emulate_B16_MM(llvm::MCInst &insn) {
2161  bool success = false;
2162  int32_t offset, pc, target;
2163  uint32_t current_inst_size = m_insn_info->get(insn.getOpcode()).getSize();
2164
2165  offset = insn.getOperand(0).getImm();
2166
2167  pc = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
2168  if (!success)
2169    return false;
2170
2171  // unconditional branch
2172  target = pc + offset;
2173
2174  Context context;
2175  context.type = eContextRelativeBranchImmediate;
2176  context.SetImmediate(current_inst_size + offset);
2177
2178  return WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2179                               target);
2180}
2181
2182/*
2183   BEQZC, BNEZC are 32 bit compact instructions without a delay slot.
2184   BEQZ16, BNEZ16 are 16 bit instructions with delay slot.
2185   BGEZALS, BLTZALS are 16 bit instructions with short (2-byte) delay slot.
2186*/
2187bool EmulateInstructionMIPS::Emulate_Branch_MM(llvm::MCInst &insn) {
2188  bool success = false;
2189  int32_t target = 0;
2190  uint32_t current_inst_size = m_insn_info->get(insn.getOpcode()).getSize();
2191  const char *op_name = m_insn_info->getName(insn.getOpcode()).data();
2192  bool update_ra = false;
2193  uint32_t ra_offset = 0;
2194
2195  /*
2196   * BEQZ16 rs, offset
2197   *      condition <- (GPR[rs] = 0)
2198   *      if condition then
2199   *          PC = PC + sign_ext (offset || 0)
2200   *
2201   * BNEZ16 rs, offset
2202   *      condition <- (GPR[rs] != 0)
2203   *      if condition then
2204   *          PC = PC + sign_ext (offset || 0)
2205   *
2206   * BEQZC rs, offset     (compact instruction: No delay slot)
2207   *      condition <- (GPR[rs] == 0)
2208   *      if condition then
2209   *         PC = PC + 4 + sign_ext (offset || 0)
2210  */
2211
2212  uint32_t rs = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
2213  int32_t offset = insn.getOperand(1).getImm();
2214
2215  int32_t pc =
2216      ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
2217  if (!success)
2218    return false;
2219
2220  int32_t rs_val = (int32_t)ReadRegisterUnsigned(
2221      eRegisterKindDWARF, dwarf_zero_mips + rs, 0, &success);
2222  if (!success)
2223    return false;
2224
2225  if (!strcasecmp(op_name, "BEQZ16_MM")) {
2226    if (rs_val == 0)
2227      target = pc + offset;
2228    else
2229      target = pc + current_inst_size +
2230               m_next_inst_size; // Skip delay slot instruction.
2231  } else if (!strcasecmp(op_name, "BNEZ16_MM")) {
2232    if (rs_val != 0)
2233      target = pc + offset;
2234    else
2235      target = pc + current_inst_size +
2236               m_next_inst_size; // Skip delay slot instruction.
2237  } else if (!strcasecmp(op_name, "BEQZC_MM")) {
2238    if (rs_val == 0)
2239      target = pc + 4 + offset;
2240    else
2241      target =
2242          pc +
2243          4; // 32 bit instruction and does not have delay slot instruction.
2244  } else if (!strcasecmp(op_name, "BNEZC_MM")) {
2245    if (rs_val != 0)
2246      target = pc + 4 + offset;
2247    else
2248      target =
2249          pc +
2250          4; // 32 bit instruction and does not have delay slot instruction.
2251  } else if (!strcasecmp(op_name, "BGEZALS_MM")) {
2252    if (rs_val >= 0)
2253      target = pc + offset;
2254    else
2255      target = pc + 6; // 32 bit instruction with short (2-byte) delay slot
2256
2257    update_ra = true;
2258    ra_offset = 6;
2259  } else if (!strcasecmp(op_name, "BLTZALS_MM")) {
2260    if (rs_val >= 0)
2261      target = pc + offset;
2262    else
2263      target = pc + 6; // 32 bit instruction with short (2-byte) delay slot
2264
2265    update_ra = true;
2266    ra_offset = 6;
2267  }
2268
2269  Context context;
2270  context.type = eContextRelativeBranchImmediate;
2271  context.SetImmediate(current_inst_size + offset);
2272
2273  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2274                             target))
2275    return false;
2276
2277  if (update_ra) {
2278    if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_ra_mips,
2279                               pc + ra_offset))
2280      return false;
2281  }
2282  return true;
2283}
2284
2285/* Emulate micromips jump instructions.
2286   JALR16,JALRS16
2287*/
2288bool EmulateInstructionMIPS::Emulate_JALRx16_MM(llvm::MCInst &insn) {
2289  bool success = false;
2290  uint32_t ra_offset = 0;
2291  const char *op_name = m_insn_info->getName(insn.getOpcode()).data();
2292
2293  uint32_t rs = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
2294
2295  uint32_t pc =
2296      ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
2297  if (!success)
2298    return false;
2299
2300  uint32_t rs_val = ReadRegisterUnsigned(eRegisterKindDWARF,
2301                                         dwarf_zero_mips + rs, 0, &success);
2302  if (!success)
2303    return false;
2304
2305  if (!strcasecmp(op_name, "JALR16_MM"))
2306    ra_offset = 6; // 2-byte instruction with 4-byte delay slot.
2307  else if (!strcasecmp(op_name, "JALRS16_MM"))
2308    ra_offset = 4; // 2-byte instruction with 2-byte delay slot.
2309
2310  Context context;
2311
2312  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2313                             rs_val))
2314    return false;
2315
2316  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_ra_mips,
2317                             pc + ra_offset))
2318    return false;
2319
2320  return true;
2321}
2322
2323/* Emulate JALS and JALX instructions.
2324    JALS 32 bit instruction with short (2-byte) delay slot.
2325    JALX 32 bit instruction with 4-byte delay slot.
2326*/
2327bool EmulateInstructionMIPS::Emulate_JALx(llvm::MCInst &insn) {
2328  bool success = false;
2329  uint32_t offset = 0, target = 0, pc = 0, ra_offset = 0;
2330  const char *op_name = m_insn_info->getName(insn.getOpcode()).data();
2331
2332  /*
2333   * JALS target
2334   *      RA = PC + 6
2335   *      offset = sign_ext (offset << 1)
2336   *      PC = PC[31-27] | offset
2337   * JALX target
2338   *      RA = PC + 8
2339   *      offset = sign_ext (offset << 2)
2340   *      PC = PC[31-28] | offset
2341  */
2342  offset = insn.getOperand(0).getImm();
2343
2344  pc = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
2345  if (!success)
2346    return false;
2347
2348  // These are PC-region branches and not PC-relative.
2349  if (!strcasecmp(op_name, "JALS_MM")) {
2350    // target address is in the ���current��� 128 MB-aligned region
2351    target = (pc & 0xF8000000UL) | offset;
2352    ra_offset = 6;
2353  } else if (!strcasecmp(op_name, "JALX_MM")) {
2354    // target address is in the ���current��� 256 MB-aligned region
2355    target = (pc & 0xF0000000UL) | offset;
2356    ra_offset = 8;
2357  }
2358
2359  Context context;
2360
2361  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2362                             target))
2363    return false;
2364
2365  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_ra_mips,
2366                             pc + ra_offset))
2367    return false;
2368
2369  return true;
2370}
2371
2372bool EmulateInstructionMIPS::Emulate_JALRS(llvm::MCInst &insn) {
2373  bool success = false;
2374  uint32_t rs = 0, rt = 0;
2375  int32_t pc = 0, rs_val = 0;
2376
2377  /*
2378      JALRS rt, rs
2379          GPR[rt] <- PC + 6
2380          PC <- GPR[rs]
2381  */
2382
2383  rt = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
2384  rs = m_reg_info->getEncodingValue(insn.getOperand(1).getReg());
2385
2386  rs_val = (int32_t)ReadRegisterUnsigned(eRegisterKindDWARF,
2387                                         dwarf_zero_mips + rs, 0, &success);
2388  if (!success)
2389    return false;
2390
2391  pc = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
2392  if (!success)
2393    return false;
2394
2395  Context context;
2396
2397  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2398                             rs_val))
2399    return false;
2400
2401  // This is 4-byte instruction with 2-byte delay slot.
2402  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_zero_mips + rt,
2403                             pc + 6))
2404    return false;
2405
2406  return true;
2407}
2408
2409bool EmulateInstructionMIPS::Emulate_BAL(llvm::MCInst &insn) {
2410  bool success = false;
2411  int32_t offset, pc, target;
2412
2413  /*
2414   * BAL offset
2415   *      offset = sign_ext (offset << 2)
2416   *      RA = PC + 8
2417   *      PC = PC + offset
2418  */
2419  offset = insn.getOperand(0).getImm();
2420
2421  pc = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
2422  if (!success)
2423    return false;
2424
2425  target = pc + offset;
2426
2427  Context context;
2428
2429  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2430                             target))
2431    return false;
2432
2433  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_ra_mips,
2434                             pc + 8))
2435    return false;
2436
2437  return true;
2438}
2439
2440bool EmulateInstructionMIPS::Emulate_BALC(llvm::MCInst &insn) {
2441  bool success = false;
2442  int32_t offset, pc, target;
2443
2444  /*
2445   * BALC offset
2446   *      offset = sign_ext (offset << 2)
2447   *      RA = PC + 4
2448   *      PC = PC + 4 + offset
2449  */
2450  offset = insn.getOperand(0).getImm();
2451
2452  pc = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
2453  if (!success)
2454    return false;
2455
2456  target = pc + offset;
2457
2458  Context context;
2459
2460  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2461                             target))
2462    return false;
2463
2464  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_ra_mips,
2465                             pc + 4))
2466    return false;
2467
2468  return true;
2469}
2470
2471bool EmulateInstructionMIPS::Emulate_BC(llvm::MCInst &insn) {
2472  bool success = false;
2473  int32_t offset, pc, target;
2474
2475  /*
2476   * BC offset
2477   *      offset = sign_ext (offset << 2)
2478   *      PC = PC + 4 + offset
2479  */
2480  offset = insn.getOperand(0).getImm();
2481
2482  pc = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
2483  if (!success)
2484    return false;
2485
2486  target = pc + offset;
2487
2488  Context context;
2489
2490  return WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2491                               target);
2492}
2493
2494bool EmulateInstructionMIPS::Emulate_J(llvm::MCInst &insn) {
2495  bool success = false;
2496  uint32_t offset, pc;
2497
2498  /*
2499   * J offset
2500   *      offset = sign_ext (offset << 2)
2501   *      PC = PC[63-28] | offset
2502  */
2503  offset = insn.getOperand(0).getImm();
2504
2505  pc = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
2506  if (!success)
2507    return false;
2508
2509  /* This is a PC-region branch and not PC-relative */
2510  pc = (pc & 0xF0000000UL) | offset;
2511
2512  Context context;
2513
2514  return WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips, pc);
2515}
2516
2517bool EmulateInstructionMIPS::Emulate_JAL(llvm::MCInst &insn) {
2518  bool success = false;
2519  uint32_t offset, target, pc;
2520
2521  /*
2522   * JAL offset
2523   *      offset = sign_ext (offset << 2)
2524   *      PC = PC[63-28] | offset
2525  */
2526  offset = insn.getOperand(0).getImm();
2527
2528  pc = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
2529  if (!success)
2530    return false;
2531
2532  /* This is a PC-region branch and not PC-relative */
2533  target = (pc & 0xF0000000UL) | offset;
2534
2535  Context context;
2536
2537  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2538                             target))
2539    return false;
2540
2541  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_ra_mips,
2542                             pc + 8))
2543    return false;
2544
2545  return true;
2546}
2547
2548bool EmulateInstructionMIPS::Emulate_JALR(llvm::MCInst &insn) {
2549  bool success = false;
2550  uint32_t rs, rt;
2551  uint32_t pc, rs_val;
2552
2553  /*
2554   * JALR rt, rs
2555   *      GPR[rt] = PC + 8
2556   *      PC = GPR[rs]
2557  */
2558  rt = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
2559  rs = m_reg_info->getEncodingValue(insn.getOperand(1).getReg());
2560
2561  pc = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
2562  if (!success)
2563    return false;
2564
2565  rs_val = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_zero_mips + rs, 0,
2566                                &success);
2567  if (!success)
2568    return false;
2569
2570  Context context;
2571
2572  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2573                             rs_val))
2574    return false;
2575
2576  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_zero_mips + rt,
2577                             pc + 8))
2578    return false;
2579
2580  return true;
2581}
2582
2583bool EmulateInstructionMIPS::Emulate_JIALC(llvm::MCInst &insn) {
2584  bool success = false;
2585  uint32_t rt;
2586  int32_t target, offset, pc, rt_val;
2587
2588  /*
2589   * JIALC rt, offset
2590   *      offset = sign_ext (offset)
2591   *      PC = GPR[rt] + offset
2592   *      RA = PC + 4
2593  */
2594  rt = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
2595  offset = insn.getOperand(1).getImm();
2596
2597  pc = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
2598  if (!success)
2599    return false;
2600
2601  rt_val = (int32_t)ReadRegisterUnsigned(eRegisterKindDWARF,
2602                                         dwarf_zero_mips + rt, 0, &success);
2603  if (!success)
2604    return false;
2605
2606  target = rt_val + offset;
2607
2608  Context context;
2609
2610  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2611                             target))
2612    return false;
2613
2614  if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_ra_mips,
2615                             pc + 4))
2616    return false;
2617
2618  return true;
2619}
2620
2621bool EmulateInstructionMIPS::Emulate_JIC(llvm::MCInst &insn) {
2622  bool success = false;
2623  uint32_t rt;
2624  int32_t target, offset, rt_val;
2625
2626  /*
2627   * JIC rt, offset
2628   *      offset = sign_ext (offset)
2629   *      PC = GPR[rt] + offset
2630  */
2631  rt = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
2632  offset = insn.getOperand(1).getImm();
2633
2634  rt_val = (int32_t)ReadRegisterUnsigned(eRegisterKindDWARF,
2635                                         dwarf_zero_mips + rt, 0, &success);
2636  if (!success)
2637    return false;
2638
2639  target = rt_val + offset;
2640
2641  Context context;
2642
2643  return WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2644                               target);
2645}
2646
2647bool EmulateInstructionMIPS::Emulate_JR(llvm::MCInst &insn) {
2648  bool success = false;
2649  uint32_t rs;
2650  uint32_t rs_val;
2651
2652  /*
2653   * JR rs
2654   *      PC = GPR[rs]
2655  */
2656  rs = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
2657
2658  rs_val = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_zero_mips + rs, 0,
2659                                &success);
2660  if (!success)
2661    return false;
2662
2663  Context context;
2664
2665  return WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2666                               rs_val);
2667}
2668
2669/*
2670    Emulate Branch on FP True/False
2671    BC1F, BC1FL :   Branch on FP False (L stands for branch likely)
2672    BC1T, BC1TL :   Branch on FP True  (L stands for branch likely)
2673*/
2674bool EmulateInstructionMIPS::Emulate_FP_branch(llvm::MCInst &insn) {
2675  bool success = false;
2676  uint32_t cc, fcsr;
2677  int32_t pc, offset, target = 0;
2678  const char *op_name = m_insn_info->getName(insn.getOpcode()).data();
2679
2680  cc = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
2681  offset = insn.getOperand(1).getImm();
2682
2683  pc = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
2684  if (!success)
2685    return false;
2686
2687  fcsr = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_fcsr_mips, 0, &success);
2688  if (!success)
2689    return false;
2690
2691  /* fcsr[23], fcsr[25-31] are vaild condition bits */
2692  fcsr = ((fcsr >> 24) & 0xfe) | ((fcsr >> 23) & 0x01);
2693
2694  if (!strcasecmp(op_name, "BC1F") || !strcasecmp(op_name, "BC1FL")) {
2695    if ((fcsr & (1 << cc)) == 0)
2696      target = pc + offset;
2697    else
2698      target = pc + 8;
2699  } else if (!strcasecmp(op_name, "BC1T") || !strcasecmp(op_name, "BC1TL")) {
2700    if ((fcsr & (1 << cc)) != 0)
2701      target = pc + offset;
2702    else
2703      target = pc + 8;
2704  }
2705  Context context;
2706
2707  return WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2708                               target);
2709}
2710
2711bool EmulateInstructionMIPS::Emulate_BC1EQZ(llvm::MCInst &insn) {
2712  bool success = false;
2713  uint32_t ft;
2714  uint32_t ft_val;
2715  int32_t target, pc, offset;
2716
2717  /*
2718   * BC1EQZ ft, offset
2719   *  condition <- (FPR[ft].bit0 == 0)
2720   *      if condition then
2721   *          offset = sign_ext (offset)
2722   *          PC = PC + 4 + offset
2723  */
2724  ft = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
2725  offset = insn.getOperand(1).getImm();
2726
2727  pc = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
2728  if (!success)
2729    return false;
2730
2731  ft_val = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_zero_mips + ft, 0,
2732                                &success);
2733  if (!success)
2734    return false;
2735
2736  if ((ft_val & 1) == 0)
2737    target = pc + 4 + offset;
2738  else
2739    target = pc + 8;
2740
2741  Context context;
2742
2743  return WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2744                               target);
2745}
2746
2747bool EmulateInstructionMIPS::Emulate_BC1NEZ(llvm::MCInst &insn) {
2748  bool success = false;
2749  uint32_t ft;
2750  uint32_t ft_val;
2751  int32_t target, pc, offset;
2752
2753  /*
2754   * BC1NEZ ft, offset
2755   *  condition <- (FPR[ft].bit0 != 0)
2756   *      if condition then
2757   *          offset = sign_ext (offset)
2758   *          PC = PC + 4 + offset
2759  */
2760  ft = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
2761  offset = insn.getOperand(1).getImm();
2762
2763  pc = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
2764  if (!success)
2765    return false;
2766
2767  ft_val = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_zero_mips + ft, 0,
2768                                &success);
2769  if (!success)
2770    return false;
2771
2772  if ((ft_val & 1) != 0)
2773    target = pc + 4 + offset;
2774  else
2775    target = pc + 8;
2776
2777  Context context;
2778
2779  return WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2780                               target);
2781}
2782
2783/*
2784    Emulate MIPS-3D Branch instructions
2785    BC1ANY2F, BC1ANY2T  : Branch on Any of Two Floating Point Condition Codes
2786   False/True
2787    BC1ANY4F, BC1ANY4T  : Branch on Any of Four Floating Point Condition Codes
2788   False/True
2789*/
2790bool EmulateInstructionMIPS::Emulate_3D_branch(llvm::MCInst &insn) {
2791  bool success = false;
2792  uint32_t cc, fcsr;
2793  int32_t pc, offset, target = 0;
2794  const char *op_name = m_insn_info->getName(insn.getOpcode()).data();
2795
2796  cc = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
2797  offset = insn.getOperand(1).getImm();
2798
2799  pc = ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
2800  if (!success)
2801    return false;
2802
2803  fcsr = (uint32_t)ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_fcsr_mips, 0,
2804                                        &success);
2805  if (!success)
2806    return false;
2807
2808  /* fcsr[23], fcsr[25-31] are vaild condition bits */
2809  fcsr = ((fcsr >> 24) & 0xfe) | ((fcsr >> 23) & 0x01);
2810
2811  if (!strcasecmp(op_name, "BC1ANY2F")) {
2812    /* if any one bit is 0 */
2813    if (((fcsr >> cc) & 3) != 3)
2814      target = pc + offset;
2815    else
2816      target = pc + 8;
2817  } else if (!strcasecmp(op_name, "BC1ANY2T")) {
2818    /* if any one bit is 1 */
2819    if (((fcsr >> cc) & 3) != 0)
2820      target = pc + offset;
2821    else
2822      target = pc + 8;
2823  } else if (!strcasecmp(op_name, "BC1ANY4F")) {
2824    /* if any one bit is 0 */
2825    if (((fcsr >> cc) & 0xf) != 0xf)
2826      target = pc + offset;
2827    else
2828      target = pc + 8;
2829  } else if (!strcasecmp(op_name, "BC1ANY4T")) {
2830    /* if any one bit is 1 */
2831    if (((fcsr >> cc) & 0xf) != 0)
2832      target = pc + offset;
2833    else
2834      target = pc + 8;
2835  }
2836  Context context;
2837
2838  return WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2839                               target);
2840}
2841
2842bool EmulateInstructionMIPS::Emulate_BNZB(llvm::MCInst &insn) {
2843  return Emulate_MSA_Branch_DF(insn, 1, true);
2844}
2845
2846bool EmulateInstructionMIPS::Emulate_BNZH(llvm::MCInst &insn) {
2847  return Emulate_MSA_Branch_DF(insn, 2, true);
2848}
2849
2850bool EmulateInstructionMIPS::Emulate_BNZW(llvm::MCInst &insn) {
2851  return Emulate_MSA_Branch_DF(insn, 4, true);
2852}
2853
2854bool EmulateInstructionMIPS::Emulate_BNZD(llvm::MCInst &insn) {
2855  return Emulate_MSA_Branch_DF(insn, 8, true);
2856}
2857
2858bool EmulateInstructionMIPS::Emulate_BZB(llvm::MCInst &insn) {
2859  return Emulate_MSA_Branch_DF(insn, 1, false);
2860}
2861
2862bool EmulateInstructionMIPS::Emulate_BZH(llvm::MCInst &insn) {
2863  return Emulate_MSA_Branch_DF(insn, 2, false);
2864}
2865
2866bool EmulateInstructionMIPS::Emulate_BZW(llvm::MCInst &insn) {
2867  return Emulate_MSA_Branch_DF(insn, 4, false);
2868}
2869
2870bool EmulateInstructionMIPS::Emulate_BZD(llvm::MCInst &insn) {
2871  return Emulate_MSA_Branch_DF(insn, 8, false);
2872}
2873
2874bool EmulateInstructionMIPS::Emulate_MSA_Branch_DF(llvm::MCInst &insn,
2875                                                   int element_byte_size,
2876                                                   bool bnz) {
2877  bool success = false, branch_hit = true;
2878  int32_t target = 0;
2879  RegisterValue reg_value;
2880  const uint8_t *ptr = nullptr;
2881
2882  uint32_t wt = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
2883  int32_t offset = insn.getOperand(1).getImm();
2884
2885  int32_t pc =
2886      ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
2887  if (!success)
2888    return false;
2889
2890  if (ReadRegister(eRegisterKindDWARF, dwarf_w0_mips + wt, reg_value))
2891    ptr = (const uint8_t *)reg_value.GetBytes();
2892  else
2893    return false;
2894
2895  for (int i = 0; i < 16 / element_byte_size; i++) {
2896    switch (element_byte_size) {
2897    case 1:
2898      if ((*ptr == 0 && bnz) || (*ptr != 0 && !bnz))
2899        branch_hit = false;
2900      break;
2901    case 2:
2902      if ((*(const uint16_t *)ptr == 0 && bnz) ||
2903          (*(const uint16_t *)ptr != 0 && !bnz))
2904        branch_hit = false;
2905      break;
2906    case 4:
2907      if ((*(const uint32_t *)ptr == 0 && bnz) ||
2908          (*(const uint32_t *)ptr != 0 && !bnz))
2909        branch_hit = false;
2910      break;
2911    case 8:
2912      if ((*(const uint64_t *)ptr == 0 && bnz) ||
2913          (*(const uint64_t *)ptr != 0 && !bnz))
2914        branch_hit = false;
2915      break;
2916    }
2917    if (!branch_hit)
2918      break;
2919    ptr = ptr + element_byte_size;
2920  }
2921
2922  if (branch_hit)
2923    target = pc + offset;
2924  else
2925    target = pc + 8;
2926
2927  Context context;
2928  context.type = eContextRelativeBranchImmediate;
2929
2930  return WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2931                               target);
2932}
2933
2934bool EmulateInstructionMIPS::Emulate_BNZV(llvm::MCInst &insn) {
2935  return Emulate_MSA_Branch_V(insn, true);
2936}
2937
2938bool EmulateInstructionMIPS::Emulate_BZV(llvm::MCInst &insn) {
2939  return Emulate_MSA_Branch_V(insn, false);
2940}
2941
2942bool EmulateInstructionMIPS::Emulate_MSA_Branch_V(llvm::MCInst &insn,
2943                                                  bool bnz) {
2944  bool success = false;
2945  int32_t target = 0;
2946  llvm::APInt wr_val = llvm::APInt::getNullValue(128);
2947  llvm::APInt fail_value = llvm::APInt::getMaxValue(128);
2948  llvm::APInt zero_value = llvm::APInt::getNullValue(128);
2949  RegisterValue reg_value;
2950
2951  uint32_t wt = m_reg_info->getEncodingValue(insn.getOperand(0).getReg());
2952  int32_t offset = insn.getOperand(1).getImm();
2953
2954  int32_t pc =
2955      ReadRegisterUnsigned(eRegisterKindDWARF, dwarf_pc_mips, 0, &success);
2956  if (!success)
2957    return false;
2958
2959  if (ReadRegister(eRegisterKindDWARF, dwarf_w0_mips + wt, reg_value))
2960    wr_val = reg_value.GetAsUInt128(fail_value);
2961  else
2962    return false;
2963
2964  if ((llvm::APInt::isSameValue(zero_value, wr_val) && !bnz) ||
2965      (!llvm::APInt::isSameValue(zero_value, wr_val) && bnz))
2966    target = pc + offset;
2967  else
2968    target = pc + 8;
2969
2970  Context context;
2971  context.type = eContextRelativeBranchImmediate;
2972
2973  return WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_pc_mips,
2974                               target);
2975}
2976
2977bool EmulateInstructionMIPS::Emulate_LDST_Imm(llvm::MCInst &insn) {
2978  bool success = false;
2979  uint32_t base;
2980  int32_t imm, address;
2981  Context bad_vaddr_context;
2982
2983  uint32_t num_operands = insn.getNumOperands();
2984  base =
2985      m_reg_info->getEncodingValue(insn.getOperand(num_operands - 2).getReg());
2986  imm = insn.getOperand(num_operands - 1).getImm();
2987
2988  RegisterInfo reg_info_base;
2989  if (!GetRegisterInfo(eRegisterKindDWARF, dwarf_zero_mips + base,
2990                       reg_info_base))
2991    return false;
2992
2993  /* read base register */
2994  address = (int32_t)ReadRegisterUnsigned(eRegisterKindDWARF,
2995                                          dwarf_zero_mips + base, 0, &success);
2996  if (!success)
2997    return false;
2998
2999  /* destination address */
3000  address = address + imm;
3001
3002  /* Set the bad_vaddr register with base address used in the instruction */
3003  bad_vaddr_context.type = eContextInvalid;
3004  WriteRegisterUnsigned(bad_vaddr_context, eRegisterKindDWARF, dwarf_bad_mips,
3005                        address);
3006
3007  return true;
3008}
3009
3010bool EmulateInstructionMIPS::Emulate_LDST_Reg(llvm::MCInst &insn) {
3011  bool success = false;
3012  uint32_t base, index;
3013  int32_t address, index_address;
3014  Context bad_vaddr_context;
3015
3016  uint32_t num_operands = insn.getNumOperands();
3017  base =
3018      m_reg_info->getEncodingValue(insn.getOperand(num_operands - 2).getReg());
3019  index =
3020      m_reg_info->getEncodingValue(insn.getOperand(num_operands - 1).getReg());
3021
3022  RegisterInfo reg_info_base, reg_info_index;
3023  if (!GetRegisterInfo(eRegisterKindDWARF, dwarf_zero_mips + base,
3024                       reg_info_base))
3025    return false;
3026
3027  if (!GetRegisterInfo(eRegisterKindDWARF, dwarf_zero_mips + index,
3028                       reg_info_index))
3029    return false;
3030
3031  /* read base register */
3032  address = (int32_t)ReadRegisterUnsigned(eRegisterKindDWARF,
3033                                          dwarf_zero_mips + base, 0, &success);
3034  if (!success)
3035    return false;
3036
3037  /* read index register */
3038  index_address = (int32_t)ReadRegisterUnsigned(
3039      eRegisterKindDWARF, dwarf_zero_mips + index, 0, &success);
3040  if (!success)
3041    return false;
3042
3043  /* destination address */
3044  address = address + index_address;
3045
3046  /* Set the bad_vaddr register with base address used in the instruction */
3047  bad_vaddr_context.type = eContextInvalid;
3048  WriteRegisterUnsigned(bad_vaddr_context, eRegisterKindDWARF, dwarf_bad_mips,
3049                        address);
3050
3051  return true;
3052}
3053