blob: d9cf2d33cf75cd0bb591fa54108144f8e8a2887e [file] [log] [blame]
Ben Murdochda12d292016-06-02 14:46:10 +01001// Copyright 2014 the V8 project authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5// A Disassembler object is used to disassemble a block of code instruction by
6// instruction. The default implementation of the NameConverter object can be
7// overriden to modify register names or to do symbol lookup on addresses.
8//
9// The example below will disassemble a block of code and print it to stdout.
10//
11// NameConverter converter;
12// Disassembler d(converter);
13// for (byte* pc = begin; pc < end;) {
14// v8::internal::EmbeddedVector<char, 256> buffer;
15// byte* prev_pc = pc;
16// pc += d.InstructionDecode(buffer, pc);
17// printf("%p %08x %s\n",
18// prev_pc, *reinterpret_cast<int32_t*>(prev_pc), buffer);
19// }
20//
21// The Disassembler class also has a convenience method to disassemble a block
22// of code into a FILE*, meaning that the above functionality could also be
23// achieved by just calling Disassembler::Disassemble(stdout, begin, end);
24
25#include <assert.h>
26#include <stdarg.h>
27#include <stdio.h>
28#include <string.h>
29
30#if V8_TARGET_ARCH_S390
31
32#include "src/base/platform/platform.h"
33#include "src/disasm.h"
34#include "src/macro-assembler.h"
35#include "src/s390/constants-s390.h"
36
37namespace v8 {
38namespace internal {
39
Ben Murdoch61f157c2016-09-16 13:49:30 +010040const auto GetRegConfig = RegisterConfiguration::Crankshaft;
41
Ben Murdochda12d292016-06-02 14:46:10 +010042//------------------------------------------------------------------------------
43
44// Decoder decodes and disassembles instructions into an output buffer.
45// It uses the converter to convert register names and call destinations into
46// more informative description.
47class Decoder {
48 public:
49 Decoder(const disasm::NameConverter& converter, Vector<char> out_buffer)
50 : converter_(converter), out_buffer_(out_buffer), out_buffer_pos_(0) {
51 out_buffer_[out_buffer_pos_] = '\0';
52 }
53
54 ~Decoder() {}
55
56 // Writes one disassembled instruction into 'buffer' (0-terminated).
57 // Returns the length of the disassembled machine instruction in bytes.
58 int InstructionDecode(byte* instruction);
59
60 private:
61 // Bottleneck functions to print into the out_buffer.
62 void PrintChar(const char ch);
63 void Print(const char* str);
64
65 // Printing of common values.
66 void PrintRegister(int reg);
67 void PrintDRegister(int reg);
68 void PrintSoftwareInterrupt(SoftwareInterruptCodes svc);
69
70 // Handle formatting of instructions and their options.
71 int FormatRegister(Instruction* instr, const char* option);
72 int FormatFloatingRegister(Instruction* instr, const char* option);
73 int FormatMask(Instruction* instr, const char* option);
74 int FormatDisplacement(Instruction* instr, const char* option);
75 int FormatImmediate(Instruction* instr, const char* option);
76 int FormatOption(Instruction* instr, const char* option);
77 void Format(Instruction* instr, const char* format);
78 void Unknown(Instruction* instr);
79 void UnknownFormat(Instruction* instr, const char* opcname);
80
81 bool DecodeTwoByte(Instruction* instr);
82 bool DecodeFourByte(Instruction* instr);
83 bool DecodeSixByte(Instruction* instr);
84
85 const disasm::NameConverter& converter_;
86 Vector<char> out_buffer_;
87 int out_buffer_pos_;
88
89 DISALLOW_COPY_AND_ASSIGN(Decoder);
90};
91
92// Support for assertions in the Decoder formatting functions.
93#define STRING_STARTS_WITH(string, compare_string) \
94 (strncmp(string, compare_string, strlen(compare_string)) == 0)
95
96// Append the ch to the output buffer.
97void Decoder::PrintChar(const char ch) { out_buffer_[out_buffer_pos_++] = ch; }
98
99// Append the str to the output buffer.
100void Decoder::Print(const char* str) {
101 char cur = *str++;
102 while (cur != '\0' && (out_buffer_pos_ < (out_buffer_.length() - 1))) {
103 PrintChar(cur);
104 cur = *str++;
105 }
106 out_buffer_[out_buffer_pos_] = 0;
107}
108
109// Print the register name according to the active name converter.
110void Decoder::PrintRegister(int reg) {
111 Print(converter_.NameOfCPURegister(reg));
112}
113
114// Print the double FP register name according to the active name converter.
115void Decoder::PrintDRegister(int reg) {
Ben Murdoch61f157c2016-09-16 13:49:30 +0100116 Print(GetRegConfig()->GetDoubleRegisterName(reg));
Ben Murdochda12d292016-06-02 14:46:10 +0100117}
118
119// Print SoftwareInterrupt codes. Factoring this out reduces the complexity of
120// the FormatOption method.
121void Decoder::PrintSoftwareInterrupt(SoftwareInterruptCodes svc) {
122 switch (svc) {
123 case kCallRtRedirected:
124 Print("call rt redirected");
125 return;
126 case kBreakpoint:
127 Print("breakpoint");
128 return;
129 default:
130 if (svc >= kStopCode) {
131 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%d - 0x%x",
132 svc & kStopCodeMask, svc & kStopCodeMask);
133 } else {
134 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%d", svc);
135 }
136 return;
137 }
138}
139
140// Handle all register based formatting in this function to reduce the
141// complexity of FormatOption.
142int Decoder::FormatRegister(Instruction* instr, const char* format) {
143 DCHECK(format[0] == 'r');
144
145 if (format[1] == '1') { // 'r1: register resides in bit 8-11
146 RRInstruction* rrinstr = reinterpret_cast<RRInstruction*>(instr);
147 int reg = rrinstr->R1Value();
148 PrintRegister(reg);
149 return 2;
150 } else if (format[1] == '2') { // 'r2: register resides in bit 12-15
151 RRInstruction* rrinstr = reinterpret_cast<RRInstruction*>(instr);
152 int reg = rrinstr->R2Value();
153 // indicating it is a r0 for displacement, in which case the offset
154 // should be 0.
155 if (format[2] == 'd') {
156 if (reg == 0) return 4;
157 PrintRegister(reg);
158 return 3;
159 } else {
160 PrintRegister(reg);
161 return 2;
162 }
163 } else if (format[1] == '3') { // 'r3: register resides in bit 16-19
164 RSInstruction* rsinstr = reinterpret_cast<RSInstruction*>(instr);
165 int reg = rsinstr->B2Value();
166 PrintRegister(reg);
167 return 2;
168 } else if (format[1] == '4') { // 'r4: register resides in bit 20-23
169 RSInstruction* rsinstr = reinterpret_cast<RSInstruction*>(instr);
170 int reg = rsinstr->B2Value();
171 PrintRegister(reg);
172 return 2;
173 } else if (format[1] == '5') { // 'r5: register resides in bit 24-28
174 RREInstruction* rreinstr = reinterpret_cast<RREInstruction*>(instr);
175 int reg = rreinstr->R1Value();
176 PrintRegister(reg);
177 return 2;
178 } else if (format[1] == '6') { // 'r6: register resides in bit 29-32
179 RREInstruction* rreinstr = reinterpret_cast<RREInstruction*>(instr);
180 int reg = rreinstr->R2Value();
181 PrintRegister(reg);
182 return 2;
183 } else if (format[1] == '7') { // 'r6: register resides in bit 32-35
184 SSInstruction* ssinstr = reinterpret_cast<SSInstruction*>(instr);
185 int reg = ssinstr->B2Value();
186 PrintRegister(reg);
187 return 2;
188 }
189
190 UNREACHABLE();
191 return -1;
192}
193
194int Decoder::FormatFloatingRegister(Instruction* instr, const char* format) {
195 DCHECK(format[0] == 'f');
196
197 // reuse 1, 5 and 6 because it is coresponding
198 if (format[1] == '1') { // 'r1: register resides in bit 8-11
199 RRInstruction* rrinstr = reinterpret_cast<RRInstruction*>(instr);
200 int reg = rrinstr->R1Value();
201 PrintDRegister(reg);
202 return 2;
203 } else if (format[1] == '2') { // 'f2: register resides in bit 12-15
204 RRInstruction* rrinstr = reinterpret_cast<RRInstruction*>(instr);
205 int reg = rrinstr->R2Value();
206 PrintDRegister(reg);
207 return 2;
208 } else if (format[1] == '3') { // 'f3: register resides in bit 16-19
209 RRDInstruction* rrdinstr = reinterpret_cast<RRDInstruction*>(instr);
210 int reg = rrdinstr->R1Value();
211 PrintDRegister(reg);
212 return 2;
213 } else if (format[1] == '5') { // 'f5: register resides in bit 24-28
214 RREInstruction* rreinstr = reinterpret_cast<RREInstruction*>(instr);
215 int reg = rreinstr->R1Value();
216 PrintDRegister(reg);
217 return 2;
218 } else if (format[1] == '6') { // 'f6: register resides in bit 29-32
219 RREInstruction* rreinstr = reinterpret_cast<RREInstruction*>(instr);
220 int reg = rreinstr->R2Value();
221 PrintDRegister(reg);
222 return 2;
223 }
224 UNREACHABLE();
225 return -1;
226}
227
228// FormatOption takes a formatting string and interprets it based on
229// the current instructions. The format string points to the first
230// character of the option string (the option escape has already been
231// consumed by the caller.) FormatOption returns the number of
232// characters that were consumed from the formatting string.
233int Decoder::FormatOption(Instruction* instr, const char* format) {
234 switch (format[0]) {
235 case 'o': {
236 if (instr->Bit(10) == 1) {
237 Print("o");
238 }
239 return 1;
240 }
241 case '.': {
242 if (instr->Bit(0) == 1) {
243 Print(".");
244 } else {
245 Print(" "); // ensure consistent spacing
246 }
247 return 1;
248 }
249 case 'r': {
250 return FormatRegister(instr, format);
251 }
252 case 'f': {
253 return FormatFloatingRegister(instr, format);
254 }
255 case 'i': { // int16
256 return FormatImmediate(instr, format);
257 }
258 case 'u': { // uint16
259 int32_t value = instr->Bits(15, 0);
260 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%d", value);
261 return 6;
262 }
263 case 'l': {
264 // Link (LK) Bit 0
265 if (instr->Bit(0) == 1) {
266 Print("l");
267 }
268 return 1;
269 }
270 case 'a': {
271 // Absolute Address Bit 1
272 if (instr->Bit(1) == 1) {
273 Print("a");
274 }
275 return 1;
276 }
277 case 't': { // 'target: target of branch instructions
278 // target26 or target16
279 DCHECK(STRING_STARTS_WITH(format, "target"));
280 if ((format[6] == '2') && (format[7] == '6')) {
281 int off = ((instr->Bits(25, 2)) << 8) >> 6;
282 out_buffer_pos_ += SNPrintF(
283 out_buffer_ + out_buffer_pos_, "%+d -> %s", off,
284 converter_.NameOfAddress(reinterpret_cast<byte*>(instr) + off));
285 return 8;
286 } else if ((format[6] == '1') && (format[7] == '6')) {
287 int off = ((instr->Bits(15, 2)) << 18) >> 16;
288 out_buffer_pos_ += SNPrintF(
289 out_buffer_ + out_buffer_pos_, "%+d -> %s", off,
290 converter_.NameOfAddress(reinterpret_cast<byte*>(instr) + off));
291 return 8;
292 }
293 case 'm': {
294 return FormatMask(instr, format);
295 }
296 }
297 case 'd': { // ds value for offset
298 return FormatDisplacement(instr, format);
299 }
300 default: {
301 UNREACHABLE();
302 break;
303 }
304 }
305
306 UNREACHABLE();
307 return -1;
308}
309
310int Decoder::FormatMask(Instruction* instr, const char* format) {
311 DCHECK(format[0] == 'm');
312 int32_t value = 0;
313 if ((format[1] == '1')) { // prints the mask format in bits 8-12
314 value = reinterpret_cast<RRInstruction*>(instr)->R1Value();
315 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "0x%x", value);
316 return 2;
317 } else if (format[1] == '2') { // mask format in bits 16-19
318 value = reinterpret_cast<RXInstruction*>(instr)->B2Value();
319 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "0x%x", value);
320 return 2;
321 } else if (format[1] == '3') { // mask format in bits 20-23
322 value = reinterpret_cast<RRFInstruction*>(instr)->M4Value();
323 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "0x%x", value);
324 return 2;
325 }
326
327 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%d", value);
328 return 2;
329}
330
331int Decoder::FormatDisplacement(Instruction* instr, const char* format) {
332 DCHECK(format[0] == 'd');
333
334 if (format[1] == '1') { // displacement in 20-31
335 RSInstruction* rsinstr = reinterpret_cast<RSInstruction*>(instr);
336 uint16_t value = rsinstr->D2Value();
337 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%d", value);
338
339 return 2;
340 } else if (format[1] == '2') { // displacement in 20-39
341 RXYInstruction* rxyinstr = reinterpret_cast<RXYInstruction*>(instr);
342 int32_t value = rxyinstr->D2Value();
343 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%d", value);
344 return 2;
345 } else if (format[1] == '4') { // SS displacement 2 36-47
346 SSInstruction* ssInstr = reinterpret_cast<SSInstruction*>(instr);
347 uint16_t value = ssInstr->D2Value();
348 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%d", value);
349 return 2;
350 } else if (format[1] == '3') { // SS displacement 1 20 - 32
351 SSInstruction* ssInstr = reinterpret_cast<SSInstruction*>(instr);
352 uint16_t value = ssInstr->D1Value();
353 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%d", value);
354 return 2;
355 } else { // s390 specific
356 int32_t value = SIGN_EXT_IMM16(instr->Bits(15, 0) & ~3);
357 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%d", value);
358 return 1;
359 }
360}
361
362int Decoder::FormatImmediate(Instruction* instr, const char* format) {
363 DCHECK(format[0] == 'i');
364
365 if (format[1] == '1') { // immediate in 16-31
366 RIInstruction* riinstr = reinterpret_cast<RIInstruction*>(instr);
367 int16_t value = riinstr->I2Value();
368 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%d", value);
369 return 2;
370 } else if (format[1] == '2') { // immediate in 16-48
371 RILInstruction* rilinstr = reinterpret_cast<RILInstruction*>(instr);
372 int32_t value = rilinstr->I2Value();
373 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%d", value);
374 return 2;
375 } else if (format[1] == '3') { // immediate in I format
376 IInstruction* iinstr = reinterpret_cast<IInstruction*>(instr);
377 int8_t value = iinstr->IValue();
378 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%d", value);
379 return 2;
380 } else if (format[1] == '4') { // immediate in 16-31, but outputs as offset
381 RIInstruction* riinstr = reinterpret_cast<RIInstruction*>(instr);
382 int16_t value = riinstr->I2Value() * 2;
383 if (value >= 0)
384 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "*+");
385 else
386 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "*");
387
388 out_buffer_pos_ += SNPrintF(
389 out_buffer_ + out_buffer_pos_, "%d -> %s", value,
390 converter_.NameOfAddress(reinterpret_cast<byte*>(instr) + value));
391 return 2;
392 } else if (format[1] == '5') { // immediate in 16-31, but outputs as offset
393 RILInstruction* rilinstr = reinterpret_cast<RILInstruction*>(instr);
394 int32_t value = rilinstr->I2Value() * 2;
395 if (value >= 0)
396 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "*+");
397 else
398 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "*");
399
400 out_buffer_pos_ += SNPrintF(
401 out_buffer_ + out_buffer_pos_, "%d -> %s", value,
402 converter_.NameOfAddress(reinterpret_cast<byte*>(instr) + value));
403 return 2;
404 } else if (format[1] == '6') { // unsigned immediate in 16-31
405 RIInstruction* riinstr = reinterpret_cast<RIInstruction*>(instr);
406 uint16_t value = riinstr->I2UnsignedValue();
407 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%d", value);
408 return 2;
409 } else if (format[1] == '7') { // unsigned immediate in 16-47
410 RILInstruction* rilinstr = reinterpret_cast<RILInstruction*>(instr);
411 uint32_t value = rilinstr->I2UnsignedValue();
412 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%d", value);
413 return 2;
414 } else if (format[1] == '8') { // unsigned immediate in 8-15
415 SSInstruction* ssinstr = reinterpret_cast<SSInstruction*>(instr);
416 uint8_t value = ssinstr->Length();
417 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%d", value);
418 return 2;
419 } else if (format[1] == '9') { // unsigned immediate in 16-23
420 RIEInstruction* rie_instr = reinterpret_cast<RIEInstruction*>(instr);
421 uint8_t value = rie_instr->I3Value();
422 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%d", value);
423 return 2;
424 } else if (format[1] == 'a') { // unsigned immediate in 24-31
425 RIEInstruction* rie_instr = reinterpret_cast<RIEInstruction*>(instr);
426 uint8_t value = rie_instr->I4Value();
427 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%d", value);
428 return 2;
429 } else if (format[1] == 'b') { // unsigned immediate in 32-39
430 RIEInstruction* rie_instr = reinterpret_cast<RIEInstruction*>(instr);
431 uint8_t value = rie_instr->I5Value();
432 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%d", value);
433 return 2;
434 } else if (format[1] == 'c') { // signed immediate in 8-15
435 SSInstruction* ssinstr = reinterpret_cast<SSInstruction*>(instr);
436 int8_t value = ssinstr->Length();
437 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%d", value);
438 return 2;
439 } else if (format[1] == 'd') { // signed immediate in 32-47
440 SILInstruction* silinstr = reinterpret_cast<SILInstruction*>(instr);
441 int16_t value = silinstr->I2Value();
442 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%d", value);
443 return 2;
444 } else if (format[1] == 'e') { // immediate in 16-47, but outputs as offset
445 RILInstruction* rilinstr = reinterpret_cast<RILInstruction*>(instr);
446 int32_t value = rilinstr->I2Value() * 2;
447 if (value >= 0)
448 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "*+");
449 else
450 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "*");
451
452 out_buffer_pos_ += SNPrintF(
453 out_buffer_ + out_buffer_pos_, "%d -> %s", value,
454 converter_.NameOfAddress(reinterpret_cast<byte*>(instr) + value));
455 return 2;
456 }
457
458 UNREACHABLE();
459 return -1;
460}
461
462// Format takes a formatting string for a whole instruction and prints it into
463// the output buffer. All escaped options are handed to FormatOption to be
464// parsed further.
465void Decoder::Format(Instruction* instr, const char* format) {
466 char cur = *format++;
467 while ((cur != 0) && (out_buffer_pos_ < (out_buffer_.length() - 1))) {
468 if (cur == '\'') { // Single quote is used as the formatting escape.
469 format += FormatOption(instr, format);
470 } else {
471 out_buffer_[out_buffer_pos_++] = cur;
472 }
473 cur = *format++;
474 }
475 out_buffer_[out_buffer_pos_] = '\0';
476}
477
478// The disassembler may end up decoding data inlined in the code. We do not want
479// it to crash if the data does not ressemble any known instruction.
480#define VERIFY(condition) \
481 if (!(condition)) { \
482 Unknown(instr); \
483 return; \
484 }
485
486// For currently unimplemented decodings the disassembler calls Unknown(instr)
487// which will just print "unknown" of the instruction bits.
488void Decoder::Unknown(Instruction* instr) { Format(instr, "unknown"); }
489
490// For currently unimplemented decodings the disassembler calls
491// UnknownFormat(instr) which will just print opcode name of the
492// instruction bits.
493void Decoder::UnknownFormat(Instruction* instr, const char* name) {
494 char buffer[100];
495 snprintf(buffer, sizeof(buffer), "%s (unknown-format)", name);
496 Format(instr, buffer);
497}
498
499// Disassembles Two Byte S390 Instructions
500// @return true if successfully decoded
501bool Decoder::DecodeTwoByte(Instruction* instr) {
502 // Print the Instruction bits.
503 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%04x ",
504 instr->InstructionBits<TwoByteInstr>());
505
506 Opcode opcode = instr->S390OpcodeValue();
507 switch (opcode) {
508 case AR:
509 Format(instr, "ar\t'r1,'r2");
510 break;
511 case SR:
512 Format(instr, "sr\t'r1,'r2");
513 break;
514 case MR:
515 Format(instr, "mr\t'r1,'r2");
516 break;
517 case DR:
518 Format(instr, "dr\t'r1,'r2");
519 break;
520 case OR:
521 Format(instr, "or\t'r1,'r2");
522 break;
523 case NR:
524 Format(instr, "nr\t'r1,'r2");
525 break;
526 case XR:
527 Format(instr, "xr\t'r1,'r2");
528 break;
529 case LR:
530 Format(instr, "lr\t'r1,'r2");
531 break;
532 case CR:
533 Format(instr, "cr\t'r1,'r2");
534 break;
535 case CLR:
536 Format(instr, "clr\t'r1,'r2");
537 break;
538 case BCR:
539 Format(instr, "bcr\t'm1,'r2");
540 break;
541 case LTR:
542 Format(instr, "ltr\t'r1,'r2");
543 break;
544 case ALR:
545 Format(instr, "alr\t'r1,'r2");
546 break;
547 case SLR:
548 Format(instr, "slr\t'r1,'r2");
549 break;
550 case LNR:
551 Format(instr, "lnr\t'r1,'r2");
552 break;
553 case LCR:
554 Format(instr, "lcr\t'r1,'r2");
555 break;
556 case BASR:
557 Format(instr, "basr\t'r1,'r2");
558 break;
559 case LDR:
560 Format(instr, "ldr\t'f1,'f2");
561 break;
562 case BKPT:
563 Format(instr, "bkpt");
564 break;
565 default:
566 return false;
567 }
568 return true;
569}
570
571// Disassembles Four Byte S390 Instructions
572// @return true if successfully decoded
573bool Decoder::DecodeFourByte(Instruction* instr) {
574 // Print the Instruction bits.
575 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%08x ",
576 instr->InstructionBits<FourByteInstr>());
577
578 Opcode opcode = instr->S390OpcodeValue();
579 switch (opcode) {
580 case AHI:
581 Format(instr, "ahi\t'r1,'i1");
582 break;
583 case AGHI:
584 Format(instr, "aghi\t'r1,'i1");
585 break;
586 case LHI:
587 Format(instr, "lhi\t'r1,'i1");
588 break;
589 case LGHI:
590 Format(instr, "lghi\t'r1,'i1");
591 break;
592 case MHI:
593 Format(instr, "mhi\t'r1,'i1");
594 break;
595 case MGHI:
596 Format(instr, "mghi\t'r1,'i1");
597 break;
598 case CHI:
599 Format(instr, "chi\t'r1,'i1");
600 break;
601 case CGHI:
602 Format(instr, "cghi\t'r1,'i1");
603 break;
604 case BRAS:
605 Format(instr, "bras\t'r1,'i1");
606 break;
607 case BRC:
608 Format(instr, "brc\t'm1,'i4");
609 break;
610 case BRCT:
611 Format(instr, "brct\t'r1,'i4");
612 break;
613 case BRCTG:
614 Format(instr, "brctg\t'r1,'i4");
615 break;
616 case IIHH:
617 Format(instr, "iihh\t'r1,'i1");
618 break;
619 case IIHL:
620 Format(instr, "iihl\t'r1,'i1");
621 break;
622 case IILH:
623 Format(instr, "iilh\t'r1,'i1");
624 break;
625 case IILL:
626 Format(instr, "iill\t'r1,'i1");
627 break;
628 case OILL:
629 Format(instr, "oill\t'r1,'i1");
630 break;
631 case TMLL:
632 Format(instr, "tmll\t'r1,'i1");
633 break;
634 case STM:
635 Format(instr, "stm\t'r1,'r2,'d1('r3)");
636 break;
637 case LM:
638 Format(instr, "lm\t'r1,'r2,'d1('r3)");
639 break;
640 case SLL:
641 Format(instr, "sll\t'r1,'d1('r3)");
642 break;
643 case SRL:
644 Format(instr, "srl\t'r1,'d1('r3)");
645 break;
646 case SLA:
647 Format(instr, "sla\t'r1,'d1('r3)");
648 break;
649 case SRA:
650 Format(instr, "sra\t'r1,'d1('r3)");
651 break;
652 case SLDL:
653 Format(instr, "sldl\t'r1,'d1('r3)");
654 break;
655 case AGR:
656 Format(instr, "agr\t'r5,'r6");
657 break;
658 case AGFR:
659 Format(instr, "agfr\t'r5,'r6");
660 break;
661 case ARK:
662 Format(instr, "ark\t'r5,'r6,'r3");
663 break;
664 case AGRK:
665 Format(instr, "agrk\t'r5,'r6,'r3");
666 break;
667 case SGR:
668 Format(instr, "sgr\t'r5,'r6");
669 break;
670 case SGFR:
671 Format(instr, "sgfr\t'r5,'r6");
672 break;
673 case SRK:
674 Format(instr, "srk\t'r5,'r6,'r3");
675 break;
676 case SGRK:
677 Format(instr, "sgrk\t'r5,'r6,'r3");
678 break;
679 case NGR:
680 Format(instr, "ngr\t'r5,'r6");
681 break;
682 case NRK:
683 Format(instr, "nrk\t'r5,'r6,'r3");
684 break;
685 case NGRK:
686 Format(instr, "ngrk\t'r5,'r6,'r3");
687 break;
688 case NILL:
689 Format(instr, "nill\t'r1,'i1");
690 break;
691 case NILH:
692 Format(instr, "nilh\t'r1,'i1");
693 break;
694 case OGR:
695 Format(instr, "ogr\t'r5,'r6");
696 break;
697 case ORK:
698 Format(instr, "ork\t'r5,'r6,'r3");
699 break;
700 case OGRK:
701 Format(instr, "ogrk\t'r5,'r6,'r3");
702 break;
703 case XGR:
704 Format(instr, "xgr\t'r5,'r6");
705 break;
706 case XRK:
707 Format(instr, "xrk\t'r5,'r6,'r3");
708 break;
709 case XGRK:
710 Format(instr, "xgrk\t'r5,'r6,'r3");
711 break;
712 case CGR:
713 Format(instr, "cgr\t'r5,'r6");
714 break;
715 case CLGR:
716 Format(instr, "clgr\t'r5,'r6");
717 break;
718 case LLGFR:
719 Format(instr, "llgfr\t'r5,'r6");
720 break;
721 case LBR:
722 Format(instr, "lbr\t'r5,'r6");
723 break;
724 case LEDBR:
725 Format(instr, "ledbr\t'f5,'f6");
726 break;
727 case LDEBR:
728 Format(instr, "ldebr\t'f5,'f6");
729 break;
730 case LTGR:
731 Format(instr, "ltgr\t'r5,'r6");
732 break;
733 case LTDBR:
734 Format(instr, "ltdbr\t'f5,'f6");
735 break;
736 case LTEBR:
737 Format(instr, "ltebr\t'f5,'f6");
738 break;
739 case LGR:
740 Format(instr, "lgr\t'r5,'r6");
741 break;
742 case LGDR:
743 Format(instr, "lgdr\t'r5,'f6");
744 break;
745 case LGFR:
746 Format(instr, "lgfr\t'r5,'r6");
747 break;
748 case LTGFR:
749 Format(instr, "ltgfr\t'r5,'r6");
750 break;
751 case LCGR:
752 Format(instr, "lcgr\t'r5,'r6");
753 break;
754 case MSR:
755 Format(instr, "msr\t'r5,'r6");
756 break;
757 case LGBR:
758 Format(instr, "lgbr\t'r5,'r6");
759 break;
760 case LGHR:
761 Format(instr, "lghr\t'r5,'r6");
762 break;
763 case MSGR:
764 Format(instr, "msgr\t'r5,'r6");
765 break;
766 case DSGR:
767 Format(instr, "dsgr\t'r5,'r6");
768 break;
769 case LZDR:
770 Format(instr, "lzdr\t'f5");
771 break;
772 case MLR:
773 Format(instr, "mlr\t'r5,'r6");
774 break;
775 case MLGR:
776 Format(instr, "mlgr\t'r5,'r6");
777 break;
778 case ALCR:
779 Format(instr, "alcr\t'r5,'r6");
780 break;
781 case ALGR:
782 Format(instr, "algr\t'r5,'r6");
783 break;
784 case ALRK:
785 Format(instr, "alrk\t'r5,'r6,'r3");
786 break;
787 case ALGRK:
788 Format(instr, "algrk\t'r5,'r6,'r3");
789 break;
790 case SLGR:
791 Format(instr, "slgr\t'r5,'r6");
792 break;
793 case SLBR:
794 Format(instr, "slbr\t'r5,'r6");
795 break;
796 case DLR:
797 Format(instr, "dlr\t'r5,'r6");
798 break;
799 case DLGR:
800 Format(instr, "dlgr\t'r5,'r6");
801 break;
802 case SLRK:
803 Format(instr, "slrk\t'r5,'r6,'r3");
804 break;
805 case SLGRK:
806 Format(instr, "slgrk\t'r5,'r6,'r3");
807 break;
808 case LHR:
809 Format(instr, "lhr\t'r5,'r6");
810 break;
811 case LLHR:
812 Format(instr, "llhr\t'r5,'r6");
813 break;
814 case LLGHR:
815 Format(instr, "llghr\t'r5,'r6");
816 break;
817 case LNGR:
818 Format(instr, "lngr\t'r5,'r6");
819 break;
820 case A:
821 Format(instr, "a\t'r1,'d1('r2d,'r3)");
822 break;
823 case S:
824 Format(instr, "s\t'r1,'d1('r2d,'r3)");
825 break;
826 case M:
827 Format(instr, "m\t'r1,'d1('r2d,'r3)");
828 break;
829 case D:
830 Format(instr, "d\t'r1,'d1('r2d,'r3)");
831 break;
832 case O:
833 Format(instr, "o\t'r1,'d1('r2d,'r3)");
834 break;
835 case N:
836 Format(instr, "n\t'r1,'d1('r2d,'r3)");
837 break;
838 case L:
839 Format(instr, "l\t'r1,'d1('r2d,'r3)");
840 break;
841 case C:
842 Format(instr, "c\t'r1,'d1('r2d,'r3)");
843 break;
844 case AH:
845 Format(instr, "ah\t'r1,'d1('r2d,'r3)");
846 break;
847 case SH:
848 Format(instr, "sh\t'r1,'d1('r2d,'r3)");
849 break;
850 case MH:
851 Format(instr, "mh\t'r1,'d1('r2d,'r3)");
852 break;
853 case AL:
854 Format(instr, "al\t'r1,'d1('r2d,'r3)");
855 break;
856 case SL:
857 Format(instr, "sl\t'r1,'d1('r2d,'r3)");
858 break;
859 case LA:
860 Format(instr, "la\t'r1,'d1('r2d,'r3)");
861 break;
862 case CH:
863 Format(instr, "ch\t'r1,'d1('r2d,'r3)");
864 break;
865 case CL:
866 Format(instr, "cl\t'r1,'d1('r2d,'r3)");
867 break;
868 case CLI:
869 Format(instr, "cli\t'd1('r3),'i8");
870 break;
871 case TM:
872 Format(instr, "tm\t'd1('r3),'i8");
873 break;
874 case BC:
875 Format(instr, "bc\t'm1,'d1('r2d,'r3)");
876 break;
877 case BCT:
878 Format(instr, "bct\t'r1,'d1('r2d,'r3)");
879 break;
880 case ST:
881 Format(instr, "st\t'r1,'d1('r2d,'r3)");
882 break;
883 case STC:
884 Format(instr, "stc\t'r1,'d1('r2d,'r3)");
885 break;
886 case IC_z:
887 Format(instr, "ic\t'r1,'d1('r2d,'r3)");
888 break;
889 case LD:
890 Format(instr, "ld\t'f1,'d1('r2d,'r3)");
891 break;
892 case LE:
893 Format(instr, "le\t'f1,'d1('r2d,'r3)");
894 break;
895 case LDGR:
896 Format(instr, "ldgr\t'f5,'r6");
897 break;
898 case STE:
899 Format(instr, "ste\t'f1,'d1('r2d,'r3)");
900 break;
901 case STD:
902 Format(instr, "std\t'f1,'d1('r2d,'r3)");
903 break;
904 case CFDBR:
905 Format(instr, "cfdbr\t'r5,'m2,'f6");
906 break;
907 case CDFBR:
908 Format(instr, "cdfbr\t'f5,'m2,'r6");
909 break;
910 case CFEBR:
911 Format(instr, "cfebr\t'r5,'m2,'f6");
912 break;
913 case CEFBR:
914 Format(instr, "cefbr\t'f5,'m2,'r6");
915 break;
916 case CGEBR:
917 Format(instr, "cgebr\t'r5,'m2,'f6");
918 break;
919 case CGDBR:
920 Format(instr, "cgdbr\t'r5,'m2,'f6");
921 break;
922 case CEGBR:
923 Format(instr, "cegbr\t'f5,'m2,'r6");
924 break;
925 case CDGBR:
926 Format(instr, "cdgbr\t'f5,'m2,'r6");
927 break;
928 case CDLFBR:
929 Format(instr, "cdlfbr\t'f5,'m2,'r6");
930 break;
931 case CDLGBR:
932 Format(instr, "cdlgbr\t'f5,'m2,'r6");
933 break;
934 case CELGBR:
935 Format(instr, "celgbr\t'f5,'m2,'r6");
936 break;
937 case CLFDBR:
938 Format(instr, "clfdbr\t'r5,'m2,'f6");
939 break;
940 case CLGDBR:
941 Format(instr, "clgdbr\t'r5,'m2,'f6");
942 break;
943 case AEBR:
944 Format(instr, "aebr\t'f5,'f6");
945 break;
946 case SEBR:
947 Format(instr, "sebr\t'f5,'f6");
948 break;
949 case MEEBR:
950 Format(instr, "meebr\t'f5,'f6");
951 break;
952 case DEBR:
953 Format(instr, "debr\t'f5,'f6");
954 break;
955 case ADBR:
956 Format(instr, "adbr\t'f5,'f6");
957 break;
958 case SDBR:
959 Format(instr, "sdbr\t'f5,'f6");
960 break;
961 case MDBR:
962 Format(instr, "mdbr\t'f5,'f6");
963 break;
964 case DDBR:
965 Format(instr, "ddbr\t'f5,'f6");
966 break;
967 case CDBR:
968 Format(instr, "cdbr\t'f5,'f6");
969 break;
970 case CEBR:
971 Format(instr, "cebr\t'f5,'f6");
972 break;
973 case SQDBR:
974 Format(instr, "sqdbr\t'f5,'f6");
975 break;
976 case SQEBR:
977 Format(instr, "sqebr\t'f5,'f6");
978 break;
979 case LCDBR:
980 Format(instr, "lcdbr\t'f5,'f6");
981 break;
982 case STH:
983 Format(instr, "sth\t'r1,'d1('r2d,'r3)");
984 break;
985 case SRDA:
986 Format(instr, "srda\t'r1,'d1('r3)");
987 break;
988 case SRDL:
989 Format(instr, "srdl\t'r1,'d1('r3)");
990 break;
991 case MADBR:
992 Format(instr, "madbr\t'f3,'f5,'f6");
993 break;
994 case MSDBR:
995 Format(instr, "msdbr\t'f3,'f5,'f6");
996 break;
997 case FLOGR:
998 Format(instr, "flogr\t'r5,'r6");
999 break;
1000 case FIEBRA:
1001 Format(instr, "fiebra\t'f5,'m2,'f6,'m3");
1002 break;
1003 case FIDBRA:
1004 Format(instr, "fidbra\t'f5,'m2,'f6,'m3");
1005 break;
1006 // TRAP4 is used in calling to native function. it will not be generated
1007 // in native code.
1008 case TRAP4: {
1009 Format(instr, "trap4");
1010 break;
1011 }
1012 default:
1013 return false;
1014 }
1015 return true;
1016}
1017
1018// Disassembles Six Byte S390 Instructions
1019// @return true if successfully decoded
1020bool Decoder::DecodeSixByte(Instruction* instr) {
1021 // Print the Instruction bits.
1022 out_buffer_pos_ +=
1023 SNPrintF(out_buffer_ + out_buffer_pos_, "%012" PRIx64 " ",
1024 instr->InstructionBits<SixByteInstr>());
1025
1026 Opcode opcode = instr->S390OpcodeValue();
1027 switch (opcode) {
1028 case LLILF:
1029 Format(instr, "llilf\t'r1,'i7");
1030 break;
1031 case LLIHF:
1032 Format(instr, "llihf\t'r1,'i7");
1033 break;
1034 case AFI:
1035 Format(instr, "afi\t'r1,'i7");
1036 break;
1037 case ASI:
1038 Format(instr, "asi\t'd2('r3),'ic");
1039 break;
1040 case AGSI:
1041 Format(instr, "agsi\t'd2('r3),'ic");
1042 break;
1043 case ALFI:
1044 Format(instr, "alfi\t'r1,'i7");
1045 break;
1046 case AHIK:
1047 Format(instr, "ahik\t'r1,'r2,'i1");
1048 break;
1049 case AGHIK:
1050 Format(instr, "aghik\t'r1,'r2,'i1");
1051 break;
1052 case CLGFI:
1053 Format(instr, "clgfi\t'r1,'i7");
1054 break;
1055 case CLFI:
1056 Format(instr, "clfi\t'r1,'i7");
1057 break;
1058 case CFI:
1059 Format(instr, "cfi\t'r1,'i2");
1060 break;
1061 case CGFI:
1062 Format(instr, "cgfi\t'r1,'i2");
1063 break;
1064 case BRASL:
1065 Format(instr, "brasl\t'r1,'ie");
1066 break;
1067 case BRCL:
1068 Format(instr, "brcl\t'm1,'i5");
1069 break;
1070 case IIHF:
1071 Format(instr, "iihf\t'r1,'i7");
1072 break;
1073 case IILF:
1074 Format(instr, "iilf\t'r1,'i7");
1075 break;
1076 case XIHF:
1077 Format(instr, "xihf\t'r1,'i7");
1078 break;
1079 case XILF:
1080 Format(instr, "xilf\t'r1,'i7");
1081 break;
1082 case SLLK:
1083 Format(instr, "sllk\t'r1,'r2,'d2('r3)");
1084 break;
1085 case SLLG:
1086 Format(instr, "sllg\t'r1,'r2,'d2('r3)");
1087 break;
1088 case RLL:
1089 Format(instr, "rll\t'r1,'r2,'d2('r3)");
1090 break;
1091 case RLLG:
1092 Format(instr, "rllg\t'r1,'r2,'d2('r3)");
1093 break;
1094 case SRLK:
1095 Format(instr, "srlk\t'r1,'r2,'d2('r3)");
1096 break;
1097 case SRLG:
1098 Format(instr, "srlg\t'r1,'r2,'d2('r3)");
1099 break;
1100 case SLAK:
1101 Format(instr, "slak\t'r1,'r2,'d2('r3)");
1102 break;
1103 case SLAG:
1104 Format(instr, "slag\t'r1,'r2,'d2('r3)");
1105 break;
1106 case SRAK:
1107 Format(instr, "srak\t'r1,'r2,'d2('r3)");
1108 break;
1109 case SRAG:
1110 Format(instr, "srag\t'r1,'r2,'d2('r3)");
1111 break;
1112 case RISBG:
1113 Format(instr, "risbg\t'r1,'r2,'i9,'ia,'ib");
1114 break;
1115 case RISBGN:
1116 Format(instr, "risbgn\t'r1,'r2,'i9,'ia,'ib");
1117 break;
1118 case LMY:
1119 Format(instr, "lmy\t'r1,'r2,'d2('r3)");
1120 break;
1121 case LMG:
1122 Format(instr, "lmg\t'r1,'r2,'d2('r3)");
1123 break;
1124 case STMY:
1125 Format(instr, "stmy\t'r1,'r2,'d2('r3)");
1126 break;
1127 case STMG:
1128 Format(instr, "stmg\t'r1,'r2,'d2('r3)");
1129 break;
1130 case LT:
1131 Format(instr, "lt\t'r1,'d2('r2d,'r3)");
1132 break;
1133 case LTG:
1134 Format(instr, "ltg\t'r1,'d2('r2d,'r3)");
1135 break;
1136 case ML:
1137 Format(instr, "ml\t'r1,'d2('r2d,'r3)");
1138 break;
1139 case AY:
1140 Format(instr, "ay\t'r1,'d2('r2d,'r3)");
1141 break;
1142 case SY:
1143 Format(instr, "sy\t'r1,'d2('r2d,'r3)");
1144 break;
1145 case NY:
1146 Format(instr, "ny\t'r1,'d2('r2d,'r3)");
1147 break;
1148 case OY:
1149 Format(instr, "oy\t'r1,'d2('r2d,'r3)");
1150 break;
1151 case XY:
1152 Format(instr, "xy\t'r1,'d2('r2d,'r3)");
1153 break;
1154 case CY:
1155 Format(instr, "cy\t'r1,'d2('r2d,'r3)");
1156 break;
1157 case AHY:
1158 Format(instr, "ahy\t'r1,'d2('r2d,'r3)");
1159 break;
1160 case SHY:
1161 Format(instr, "shy\t'r1,'d2('r2d,'r3)");
1162 break;
1163 case LGH:
1164 Format(instr, "lgh\t'r1,'d2('r2d,'r3)");
1165 break;
1166 case AG:
1167 Format(instr, "ag\t'r1,'d2('r2d,'r3)");
1168 break;
1169 case AGF:
1170 Format(instr, "agf\t'r1,'d2('r2d,'r3)");
1171 break;
1172 case SG:
1173 Format(instr, "sg\t'r1,'d2('r2d,'r3)");
1174 break;
1175 case NG:
1176 Format(instr, "ng\t'r1,'d2('r2d,'r3)");
1177 break;
1178 case OG:
1179 Format(instr, "og\t'r1,'d2('r2d,'r3)");
1180 break;
1181 case XG:
1182 Format(instr, "xg\t'r1,'d2('r2d,'r3)");
1183 break;
1184 case CG:
1185 Format(instr, "cg\t'r1,'d2('r2d,'r3)");
1186 break;
1187 case LB:
1188 Format(instr, "lb\t'r1,'d2('r2d,'r3)");
1189 break;
1190 case LG:
1191 Format(instr, "lg\t'r1,'d2('r2d,'r3)");
1192 break;
1193 case LGF:
1194 Format(instr, "lgf\t'r1,'d2('r2d,'r3)");
1195 break;
1196 case LLGF:
1197 Format(instr, "llgf\t'r1,'d2('r2d,'r3)");
1198 break;
1199 case LY:
1200 Format(instr, "ly\t'r1,'d2('r2d,'r3)");
1201 break;
1202 case ALY:
1203 Format(instr, "aly\t'r1,'d2('r2d,'r3)");
1204 break;
1205 case ALG:
1206 Format(instr, "alg\t'r1,'d2('r2d,'r3)");
1207 break;
1208 case SLG:
1209 Format(instr, "slg\t'r1,'d2('r2d,'r3)");
1210 break;
1211 case SGF:
1212 Format(instr, "sgf\t'r1,'d2('r2d,'r3)");
1213 break;
1214 case SLY:
1215 Format(instr, "sly\t'r1,'d2('r2d,'r3)");
1216 break;
1217 case LLH:
1218 Format(instr, "llh\t'r1,'d2('r2d,'r3)");
1219 break;
1220 case LLGH:
1221 Format(instr, "llgh\t'r1,'d2('r2d,'r3)");
1222 break;
1223 case LLC:
1224 Format(instr, "llc\t'r1,'d2('r2d,'r3)");
1225 break;
1226 case LLGC:
1227 Format(instr, "llgc\t'r1,'d2('r2d,'r3)");
1228 break;
1229 case LDEB:
1230 Format(instr, "ldeb\t'f1,'d2('r2d,'r3)");
1231 break;
1232 case LAY:
1233 Format(instr, "lay\t'r1,'d2('r2d,'r3)");
1234 break;
1235 case LARL:
1236 Format(instr, "larl\t'r1,'i5");
1237 break;
1238 case LGB:
1239 Format(instr, "lgb\t'r1,'d2('r2d,'r3)");
1240 break;
1241 case CHY:
1242 Format(instr, "chy\t'r1,'d2('r2d,'r3)");
1243 break;
1244 case CLY:
1245 Format(instr, "cly\t'r1,'d2('r2d,'r3)");
1246 break;
1247 case CLIY:
1248 Format(instr, "cliy\t'd2('r3),'i8");
1249 break;
1250 case TMY:
1251 Format(instr, "tmy\t'd2('r3),'i8");
1252 break;
1253 case CLG:
1254 Format(instr, "clg\t'r1,'d2('r2d,'r3)");
1255 break;
1256 case BCTG:
1257 Format(instr, "bctg\t'r1,'d2('r2d,'r3)");
1258 break;
1259 case STY:
1260 Format(instr, "sty\t'r1,'d2('r2d,'r3)");
1261 break;
1262 case STG:
1263 Format(instr, "stg\t'r1,'d2('r2d,'r3)");
1264 break;
1265 case ICY:
1266 Format(instr, "icy\t'r1,'d2('r2d,'r3)");
1267 break;
1268 case MVC:
1269 Format(instr, "mvc\t'd3('i8,'r3),'d4('r7)");
1270 break;
1271 case MVHI:
1272 Format(instr, "mvhi\t'd3('r3),'id");
1273 break;
1274 case MVGHI:
1275 Format(instr, "mvghi\t'd3('r3),'id");
1276 break;
1277 case ALGFI:
1278 Format(instr, "algfi\t'r1,'i7");
1279 break;
1280 case SLGFI:
1281 Format(instr, "slgfi\t'r1,'i7");
1282 break;
1283 case SLFI:
1284 Format(instr, "slfi\t'r1,'i7");
1285 break;
1286 case NIHF:
1287 Format(instr, "nihf\t'r1,'i7");
1288 break;
1289 case NILF:
1290 Format(instr, "nilf\t'r1,'i7");
1291 break;
1292 case OIHF:
1293 Format(instr, "oihf\t'r1,'i7");
1294 break;
1295 case OILF:
1296 Format(instr, "oilf\t'r1,'i7");
1297 break;
1298 case MSFI:
1299 Format(instr, "msfi\t'r1,'i7");
1300 break;
1301 case MSGFI:
1302 Format(instr, "msgfi\t'r1,'i7");
1303 break;
1304 case LDY:
1305 Format(instr, "ldy\t'f1,'d2('r2d,'r3)");
1306 break;
1307 case LEY:
1308 Format(instr, "ley\t'f1,'d2('r2d,'r3)");
1309 break;
1310 case STEY:
1311 Format(instr, "stey\t'f1,'d2('r2d,'r3)");
1312 break;
1313 case STDY:
1314 Format(instr, "stdy\t'f1,'d2('r2d,'r3)");
1315 break;
1316 case ADB:
1317 Format(instr, "adb\t'r1,'d1('r2d, 'r3)");
1318 break;
1319 case SDB:
1320 Format(instr, "sdb\t'r1,'d1('r2d, 'r3)");
1321 break;
1322 case MDB:
1323 Format(instr, "mdb\t'r1,'d1('r2d, 'r3)");
1324 break;
1325 case DDB:
1326 Format(instr, "ddb\t'r1,'d1('r2d, 'r3)");
1327 break;
1328 case SQDB:
1329 Format(instr, "sqdb\t'r1,'d1('r2d, 'r3)");
1330 break;
1331 default:
1332 return false;
1333 }
1334 return true;
1335}
1336
1337#undef VERIFIY
1338
1339// Disassemble the instruction at *instr_ptr into the output buffer.
1340int Decoder::InstructionDecode(byte* instr_ptr) {
1341 Instruction* instr = Instruction::At(instr_ptr);
1342 int instrLength = instr->InstructionLength();
1343
1344 if (2 == instrLength)
1345 DecodeTwoByte(instr);
1346 else if (4 == instrLength)
1347 DecodeFourByte(instr);
1348 else
1349 DecodeSixByte(instr);
1350
1351 return instrLength;
1352}
1353
1354} // namespace internal
1355} // namespace v8
1356
1357//------------------------------------------------------------------------------
1358
1359namespace disasm {
1360
1361const char* NameConverter::NameOfAddress(byte* addr) const {
Ben Murdoch61f157c2016-09-16 13:49:30 +01001362 v8::internal::SNPrintF(tmp_buffer_, "%p", static_cast<void*>(addr));
Ben Murdochda12d292016-06-02 14:46:10 +01001363 return tmp_buffer_.start();
1364}
1365
1366const char* NameConverter::NameOfConstant(byte* addr) const {
1367 return NameOfAddress(addr);
1368}
1369
1370const char* NameConverter::NameOfCPURegister(int reg) const {
Ben Murdoch61f157c2016-09-16 13:49:30 +01001371 return v8::internal::GetRegConfig()->GetGeneralRegisterName(reg);
Ben Murdochda12d292016-06-02 14:46:10 +01001372}
1373
1374const char* NameConverter::NameOfByteCPURegister(int reg) const {
1375 UNREACHABLE(); // S390 does not have the concept of a byte register
1376 return "nobytereg";
1377}
1378
1379const char* NameConverter::NameOfXMMRegister(int reg) const {
1380 // S390 does not have XMM register
1381 // TODO(joransiu): Consider update this for Vector Regs
1382 UNREACHABLE();
1383 return "noxmmreg";
1384}
1385
1386const char* NameConverter::NameInCode(byte* addr) const {
1387 // The default name converter is called for unknown code. So we will not try
1388 // to access any memory.
1389 return "";
1390}
1391
1392//------------------------------------------------------------------------------
1393
1394Disassembler::Disassembler(const NameConverter& converter)
1395 : converter_(converter) {}
1396
1397Disassembler::~Disassembler() {}
1398
1399int Disassembler::InstructionDecode(v8::internal::Vector<char> buffer,
1400 byte* instruction) {
1401 v8::internal::Decoder d(converter_, buffer);
1402 return d.InstructionDecode(instruction);
1403}
1404
1405// The S390 assembler does not currently use constant pools.
1406int Disassembler::ConstantPoolSizeAt(byte* instruction) { return -1; }
1407
1408void Disassembler::Disassemble(FILE* f, byte* begin, byte* end) {
1409 NameConverter converter;
1410 Disassembler d(converter);
1411 for (byte* pc = begin; pc < end;) {
1412 v8::internal::EmbeddedVector<char, 128> buffer;
1413 buffer[0] = '\0';
1414 byte* prev_pc = pc;
1415 pc += d.InstructionDecode(buffer, pc);
Ben Murdoch61f157c2016-09-16 13:49:30 +01001416 v8::internal::PrintF(f, "%p %08x %s\n", static_cast<void*>(prev_pc),
Ben Murdochda12d292016-06-02 14:46:10 +01001417 *reinterpret_cast<int32_t*>(prev_pc), buffer.start());
1418 }
1419}
1420
1421} // namespace disasm
1422
1423#endif // V8_TARGET_ARCH_S390