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