/* * @(#)MethodInfo.java 1.4 95/08/16 Chuck McManis * * Copyright (c) 1996 Chuck McManis, All Rights Reserved. * * Permission to use, copy, modify, and distribute this software * and its documentation for NON-COMMERCIAL purposes and without * fee is hereby granted provided that this copyright notice * appears in all copies. * * CHUCK MCMANIS MAKES NO REPRESENTATIONS OR WARRANTIES ABOUT THE SUITABILITY * OF THE SOFTWARE, EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED * TO THE IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR A * PARTICULAR PURPOSE, OR NON-INFRINGEMENT. CHUCK MCMANIS SHALL NOT BE * LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF USING, * MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS DERIVATIVES. */ package util; import java.io.DataInputStream; import java.io.DataOutputStream; import java.io.IOException; /** * This class describes a Method as it is stored in the class file. * The attribute associated with method is the code that actually implements * the method. Since we don't need to manipulate the byte codes directly * we leave them as an opaque chunk in the attributes[] array. References * in the code are all references into the constant table so when we are * modifing a class to use a different object we needn't get into the code * level. * * @version 1.4, 16 Aug 1995 * @author Chuck McManis * @see ClassFile */ public class MethodInfo { short accessFlags; ConstantPoolInfo name; ConstantPoolInfo signature; AttributeInfo attributes[]; /** * Read a method_info from the data stream. */ public boolean read(DataInputStream di, ConstantPoolInfo pool[]) throws IOException { int count; accessFlags = di.readShort(); name = pool[di.readShort()]; signature = pool[di.readShort()]; count = di.readShort(); if (count != 0) { attributes = new AttributeInfo[count]; for (int i = 0; i < count; i++) { attributes[i] = new AttributeInfo(); // "code" if (! attributes[i].read(di, pool)) { return (false); } } } return (true); } /** * Write out a method_info, do constant table fixups on the write. */ public void write(DataOutputStream dos, ConstantPoolInfo pool[]) throws IOException, Exception { dos.writeShort(accessFlags); dos.writeShort(ConstantPoolInfo.indexOf(name, pool)); dos.writeShort(ConstantPoolInfo.indexOf(signature, pool)); if (attributes == null) { dos.writeShort(0); } else { dos.writeShort(attributes.length); for (int i = 0; i < attributes.length; i++) attributes[i].write(dos, pool); } } /** * print out the method, much as you would see it in the source * file. The string ClassName is substituted for <init> when * printing. */ public String toString(String className) { StringBuffer x = new StringBuffer(); boolean isArray = false; String paramSig; String returnSig; int ndx = 0; StringBuffer parameterList = new StringBuffer(); char initialParameter = 'a'; StringBuffer varName = new StringBuffer(); String s = signature.strValue; paramSig = s.substring(s.indexOf('(')+1, s.indexOf(')')); returnSig = s.substring(s.indexOf(')')+1); x.append(ClassFile.accessString(accessFlags)); /* catch constructors */ if ((className != null) && (name.toString().startsWith(""))) parameterList.append(className); else parameterList.append(name.toString()); parameterList.append("("); if ((paramSig.length() > 0) && paramSig.charAt(0) != 'V') { while (paramSig.length() > 0) { varName.setLength(0); varName.append(initialParameter); initialParameter++; parameterList.append( ClassFile.typeString(paramSig, varName.toString())); paramSig = ClassFile.nextSig(paramSig); if (paramSig.length() > 0) parameterList.append(", "); } } parameterList.append(")"); x.append(ClassFile.typeString(returnSig, parameterList.toString())); x.append(";"); return (x.toString()); } /** * Generic toString method, init method is unchanged. */ public String toString() { return (toString((String)null)); } }