1 /* 2 * reserved comment block 3 * DO NOT REMOVE OR ALTER! 4 */ 5 /* 6 * Licensed to the Apache Software Foundation (ASF) under one or more 7 * contributor license agreements. See the NOTICE file distributed with 8 * this work for additional information regarding copyright ownership. 9 * The ASF licenses this file to You under the Apache License, Version 2.0 10 * (the "License"); you may not use this file except in compliance with 11 * the License. You may obtain a copy of the License at 12 * 13 * http://www.apache.org/licenses/LICENSE-2.0 14 * 15 * Unless required by applicable law or agreed to in writing, software 16 * distributed under the License is distributed on an "AS IS" BASIS, 17 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 18 * See the License for the specific language governing permissions and 19 * limitations under the License. 20 */ 21 22 package com.sun.org.apache.bcel.internal.generic; 23 24 import java.io.DataOutputStream; 25 import java.io.IOException; 26 27 import com.sun.org.apache.bcel.internal.util.ByteSequence; 28 29 /** 30 * IINC - Increment local variable by constant 31 * 32 * @version $Id$ 33 */ 34 public class IINC extends LocalVariableInstruction { 35 36 private boolean wide; 37 private int c; 38 39 40 /** 41 * Empty constructor needed for Instruction.readInstruction. 42 * Not to be used otherwise. 43 */ 44 IINC() { 45 } 46 47 48 /** 49 * @param n index of local variable 50 * @param c increment factor 51 */ 52 public IINC(final int n, final int c) { 53 super(); // Default behaviour of LocalVariableInstruction causes error 54 super.setOpcode(com.sun.org.apache.bcel.internal.Const.IINC); 55 super.setLength((short) 3); 56 setIndex(n); // May set wide as side effect 57 setIncrement(c); 58 } 59 60 61 /** 62 * Dump instruction as byte code to stream out. 63 * @param out Output stream 64 */ 65 @Override 66 public void dump( final DataOutputStream out ) throws IOException { 67 if (wide) { 68 out.writeByte(com.sun.org.apache.bcel.internal.Const.WIDE); 69 } 70 out.writeByte(super.getOpcode()); 71 if (wide) { 72 out.writeShort(super.getIndex()); 73 out.writeShort(c); 74 } else { 75 out.writeByte(super.getIndex()); 76 out.writeByte(c); 77 } 78 } 79 80 81 private void setWide() { 82 wide = super.getIndex() > com.sun.org.apache.bcel.internal.Const.MAX_BYTE; 83 if (c > 0) { 84 wide = wide || (c > Byte.MAX_VALUE); 85 } else { 86 wide = wide || (c < Byte.MIN_VALUE); 87 } 88 if (wide) { 89 super.setLength(6); // wide byte included 90 } else { 91 super.setLength(3); 92 } 93 } 94 95 96 /** 97 * Read needed data (e.g. index) from file. 98 */ 99 @Override 100 protected void initFromFile( final ByteSequence bytes, final boolean wide ) throws IOException { 101 this.wide = wide; 102 if (wide) { 103 super.setLength(6); 104 super.setIndexOnly(bytes.readUnsignedShort()); 105 c = bytes.readShort(); 106 } else { 107 super.setLength(3); 108 super.setIndexOnly(bytes.readUnsignedByte()); 109 c = bytes.readByte(); 110 } 111 } 112 113 114 /** 115 * @return mnemonic for instruction 116 */ 117 @Override 118 public String toString( final boolean verbose ) { 119 return super.toString(verbose) + " " + c; 120 } 121 122 123 /** 124 * Set index of local variable. 125 */ 126 @Override 127 public final void setIndex( final int n ) { 128 if (n < 0) { 129 throw new ClassGenException("Negative index value: " + n); 130 } 131 super.setIndexOnly(n); 132 setWide(); 133 } 134 135 136 /** 137 * @return increment factor 138 */ 139 public final int getIncrement() { 140 return c; 141 } 142 143 144 /** 145 * Set increment factor. 146 */ 147 public final void setIncrement( final int c ) { 148 this.c = c; 149 setWide(); 150 } 151 152 153 /** @return int type 154 */ 155 @Override 156 public Type getType( final ConstantPoolGen cp ) { 157 return Type.INT; 158 } 159 160 161 /** 162 * Call corresponding visitor method(s). The order is: 163 * Call visitor methods of implemented interfaces first, then 164 * call methods according to the class hierarchy in descending order, 165 * i.e., the most specific visitXXX() call comes last. 166 * 167 * @param v Visitor object 168 */ 169 @Override 170 public void accept( final Visitor v ) { 171 v.visitLocalVariableInstruction(this); 172 v.visitIINC(this); 173 } 174 }