hotspot/agent/src/share/classes/sun/jvm/hotspot/asm/sparc/SPARCDisassembler.java
changeset 13903 eebf638312d2
parent 13902 6408a49a3a6b
parent 13901 4897299f395b
child 13905 12e9215f3daa
equal deleted inserted replaced
13902:6408a49a3a6b 13903:eebf638312d2
     1 /*
       
     2  * Copyright (c) 2002, Oracle and/or its affiliates. All rights reserved.
       
     3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
       
     4  *
       
     5  * This code is free software; you can redistribute it and/or modify it
       
     6  * under the terms of the GNU General Public License version 2 only, as
       
     7  * published by the Free Software Foundation.
       
     8  *
       
     9  * This code is distributed in the hope that it will be useful, but WITHOUT
       
    10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
       
    11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
       
    12  * version 2 for more details (a copy is included in the LICENSE file that
       
    13  * accompanied this code).
       
    14  *
       
    15  * You should have received a copy of the GNU General Public License version
       
    16  * 2 along with this work; if not, write to the Free Software Foundation,
       
    17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
       
    18  *
       
    19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
       
    20  * or visit www.oracle.com if you need additional information or have any
       
    21  * questions.
       
    22  *
       
    23  */
       
    24 
       
    25 package sun.jvm.hotspot.asm.sparc;
       
    26 
       
    27 import sun.jvm.hotspot.asm.*;
       
    28 import java.io.*;
       
    29 import java.util.*;
       
    30 
       
    31 public abstract class SPARCDisassembler extends Disassembler
       
    32                     implements /* imports */ SPARCOpcodes, RTLDataTypes, RTLOperations {
       
    33 
       
    34     // instruction cache - Map<Integer, Instruction>.
       
    35     protected static Map instructionCache = new HashMap();
       
    36     protected final SPARCInstructionFactory factory;
       
    37 
       
    38     public SPARCDisassembler(long startPc, byte[] code, SPARCInstructionFactory factory) {
       
    39         super(startPc, code);
       
    40         this.factory = factory;
       
    41     }
       
    42 
       
    43     protected static InstructionDecoder illegalDecoder = new IllegalInstructionDecoder();
       
    44     protected static InstructionDecoder callDecoder = new CallDecoder();
       
    45 
       
    46     // direct call instruction
       
    47     protected Instruction decodeFormat1Instruction(int instruction) {
       
    48         return callDecoder.decode(instruction, factory);
       
    49     }
       
    50 
       
    51     protected abstract InstructionDecoder getFormat2Decoder(int op2);
       
    52 
       
    53     protected Instruction decodeFormat2Instruction(int instruction) {
       
    54         int op2 = (instruction & OP_2_MASK) >>> OP_2_START_BIT;
       
    55         InstructionDecoder decoder = getFormat2Decoder(op2);
       
    56         return decoder.decode(instruction, factory);
       
    57     }
       
    58 
       
    59     // "op3" - used in format 3 & 3A instructions - 6 bits width
       
    60 
       
    61     protected static int getOp3(int instruction) {
       
    62         return (instruction & OP_3_MASK) >>> OP_3_START_BIT;
       
    63     }
       
    64 
       
    65     // op3 opcodes is broken up into column and row. MSB 2 bits form column.
       
    66     // LSB 4 bits form row number.
       
    67 
       
    68     protected static int getOp3Row(int op3) {
       
    69         return op3 & 0xF;
       
    70     }
       
    71 
       
    72     protected static int getOp3Column(int op3) {
       
    73         return (op3 >>> 4) & 0x3;
       
    74     }
       
    75 
       
    76     protected abstract InstructionDecoder getFormat3Decoder(int row, int column);
       
    77 
       
    78     // memory instructions
       
    79     protected Instruction decodeFormat3Instruction(int instruction) {
       
    80         int op3 = getOp3(instruction);
       
    81         int row = getOp3Row(op3);
       
    82         int column = getOp3Column(op3);
       
    83         return getFormat3Decoder(row, column).decode(instruction, factory);
       
    84     }
       
    85 
       
    86     protected abstract InstructionDecoder getFormat3ADecoder(int row, int column);
       
    87 
       
    88     // arithmetic, logic, shift and the rest
       
    89     protected Instruction decodeFormat3AInstruction(int instruction) {
       
    90         int op3 = getOp3(instruction);
       
    91         int row = getOp3Row(op3);
       
    92         int column = getOp3Column(op3);
       
    93         return getFormat3ADecoder(row, column).decode(instruction, factory);
       
    94     }
       
    95 
       
    96     public void decode(InstructionVisitor visitor) {
       
    97         visitor.prologue();
       
    98         try {
       
    99             DataInputStream dis = new DataInputStream(new ByteArrayInputStream(code));
       
   100             int instruction = -1;
       
   101             int format = -1;
       
   102             Instruction instr = null;
       
   103             int len = 0;
       
   104 
       
   105             while (len < code.length) {
       
   106                 instr = null;
       
   107                 instruction =  dis.readInt();
       
   108                 // check whether we have this in cache.
       
   109                 instr = (Instruction) instructionCache.get(new Integer(instruction));
       
   110                 if (instr == null) {
       
   111                     format = (instruction & FORMAT_MASK) >>> FORMAT_START_BIT;
       
   112 
       
   113                     switch (format) {
       
   114                         case FORMAT_2:  // 0
       
   115                             instr = decodeFormat2Instruction(instruction);
       
   116                             break;
       
   117 
       
   118                         case FORMAT_1:  // 1
       
   119                             instr = decodeFormat1Instruction(instruction);
       
   120                             break;
       
   121 
       
   122                         case FORMAT_3A: // 2
       
   123                             instr = decodeFormat3AInstruction(instruction);
       
   124                             break;
       
   125 
       
   126                         case FORMAT_3:  // 3
       
   127                             instr = decodeFormat3Instruction(instruction);
       
   128                             break;
       
   129                     }
       
   130 
       
   131                     // add the new instruction to cache.
       
   132                     instructionCache.put(new Integer(instruction), instr);
       
   133                 }
       
   134 
       
   135                 visitor.visit(startPc + len, instr);
       
   136                 len += 4;
       
   137             }
       
   138         } catch (IOException ioExp) {
       
   139             // ignore, can't happen
       
   140         } finally {
       
   141             visitor.epilogue();
       
   142         }
       
   143     }
       
   144 }