View Javadoc

    1   /*
    2    * Copyright  2000-2004 The Apache Software Foundation
    3    *
    4    *  Licensed under the Apache License, Version 2.0 (the "License");
    5    *  you may not use this file except in compliance with the License.
    6    *  You may obtain a copy of the License at
    7    *
    8    *      http://www.apache.org/licenses/LICENSE-2.0
    9    *
    10   *  Unless required by applicable law or agreed to in writing, software
    11   *  distributed under the License is distributed on an "AS IS" BASIS,
    12   *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    13   *  See the License for the specific language governing permissions and
    14   *  limitations under the License.
    15   *
    16   */
    17  package org.apache.bcel.verifier.statics;
    18
    19
    20  import org.apache.bcel.classfile.Code;
    21  import org.apache.bcel.classfile.CodeException;
    22  import org.apache.bcel.classfile.ConstantClass;
    23  import org.apache.bcel.classfile.ConstantDouble;
    24  import org.apache.bcel.classfile.ConstantFieldref;
    25  import org.apache.bcel.classfile.ConstantFloat;
    26  import org.apache.bcel.classfile.ConstantInteger;
    27  import org.apache.bcel.classfile.ConstantInterfaceMethodref;
    28  import org.apache.bcel.classfile.ConstantLong;
    29  import org.apache.bcel.classfile.ConstantMethodref;
    30  import org.apache.bcel.classfile.ConstantNameAndType;
    31  import org.apache.bcel.classfile.ConstantPool;
    32  import org.apache.bcel.classfile.ConstantString;
    33  import org.apache.bcel.classfile.ConstantUtf8;
    34  import org.apache.bcel.classfile.ConstantValue;
    35  import org.apache.bcel.classfile.Deprecated;
    36  import org.apache.bcel.classfile.ExceptionTable;
    37  import org.apache.bcel.classfile.Field;
    38  import org.apache.bcel.classfile.InnerClass;
    39  import org.apache.bcel.classfile.InnerClasses;
    40  import org.apache.bcel.classfile.JavaClass;
    41  import org.apache.bcel.classfile.LineNumber;
    42  import org.apache.bcel.classfile.LineNumberTable;
    43  import org.apache.bcel.classfile.LocalVariable;
    44  import org.apache.bcel.classfile.LocalVariableTable;
    45  import org.apache.bcel.classfile.Method;
    46  import org.apache.bcel.classfile.Node;
    47  import org.apache.bcel.classfile.Signature;
    48  import org.apache.bcel.classfile.SourceFile;
    49  import org.apache.bcel.classfile.StackMap;
    50  import org.apache.bcel.classfile.Synthetic;
    51  import org.apache.bcel.classfile.Unknown;
    52  import org.apache.bcel.classfile.Visitor;
    53  import org.apache.bcel.verifier.exc.AssertionViolatedException;
    54
    55  /***
    56   * BCEL's Node classes (those from the classfile API that <B>accept()</B> Visitor
    57   * instances) have <B>toString()</B> methods that were not designed to be robust,
    58   * this gap is closed by this class.
    59   * When performing class file verification, it may be useful to output which
    60   * entity (e.g. a <B>Code</B> instance) is not satisfying the verifier's
    61   * constraints, but in this case it could be possible for the <B>toString()</B>
    62   * method to throw a RuntimeException.
    63   * A (new StringRepresentation(Node n)).toString() never throws any exception.
    64   * Note that this class also serves as a placeholder for more sophisticated message
    65   * handling in future versions of JustIce.
    66   *
    67   * @version $Id: StringRepresentation.java 386056 2006-03-15 11:31:56Z tcurdt $
    68   * @author Enver Haase
    69   */
    70  public class StringRepresentation extends org.apache.bcel.classfile.EmptyVisitor implements Visitor {
    71      /*** The string representation, created by a visitXXX() method, output by toString(). */
    72      private String tostring;
    73      /*** The node we ask for its string representation. Not really needed; only for debug output. */
    74      private Node n;
    75
    76      /***
    77       * Creates a new StringRepresentation object which is the representation of n.
    78       *
    79       * @see #toString()
    80       */
    81      public StringRepresentation(Node n) {
    82          this.n = n;
    83          n.accept(this); // assign a string representation to field 'tostring' if we know n's class.
    84      }
    85
    86      /***
    87       * Returns the String representation.
    88       */
    89      public String toString() {
    90  // The run-time check below is needed because we don't want to omit inheritance
    91  // of "EmptyVisitor" and provide a thousand empty methods.
    92  // However, in terms of performance this would be a better idea.
    93  // If some new "Node" is defined in BCEL (such as some concrete "Attribute"), we
    94  // want to know that this class has also to be adapted.
    95          if (tostring == null) {
    96              throw new AssertionViolatedException("Please adapt '" + getClass() + "' to deal with objects of class '" + n.getClass() + "'.");
    97          }
    98          return tostring;
    99      }
    100
    101     /***
    102      * Returns the String representation of the Node object obj;
    103      * this is obj.toString() if it does not throw any RuntimeException,
    104      * or else it is a string derived only from obj's class name.
    105      */
    106     private String toString(Node obj) {
    107         String ret;
    108         try {
    109             ret = obj.toString();
    110         }
    111         catch (RuntimeException e) { // including ClassFormatException, trying to convert the "signature" of a ReturnaddressType LocalVariable (shouldn't occur, but people do crazy things)
    112             String s = obj.getClass().getName();
    113             s = s.substring(s.lastIndexOf(".") + 1);
    114             ret = "<<" + s + ">>";
    115         }
    116         return ret;
    117     }
    118
    119     ////////////////////////////////
    120     // Visitor methods start here //
    121     ////////////////////////////////
    122     // We don't of course need to call some default implementation:
    123     // e.g. we could also simply output "Code" instead of a possibly
    124     // lengthy Code attribute's toString().
    125     public void visitCode(Code obj) {
    126         //tostring = toString(obj);
    127         tostring = "<CODE>"; // We don't need real code outputs.
    128     }
    129
    130     public void visitCodeException(CodeException obj) {
    131         tostring = toString(obj);
    132     }
    133
    134     public void visitConstantClass(ConstantClass obj) {
    135         tostring = toString(obj);
    136     }
    137
    138     public void visitConstantDouble(ConstantDouble obj) {
    139         tostring = toString(obj);
    140     }
    141
    142     public void visitConstantFieldref(ConstantFieldref obj) {
    143         tostring = toString(obj);
    144     }
    145
    146     public void visitConstantFloat(ConstantFloat obj) {
    147         tostring = toString(obj);
    148     }
    149
    150     public void visitConstantInteger(ConstantInteger obj) {
    151         tostring = toString(obj);
    152     }
    153
    154     public void visitConstantInterfaceMethodref(ConstantInterfaceMethodref obj) {
    155         tostring = toString(obj);
    156     }
    157
    158     public void visitConstantLong(ConstantLong obj) {
    159         tostring = toString(obj);
    160     }
    161
    162     public void visitConstantMethodref(ConstantMethodref obj) {
    163         tostring = toString(obj);
    164     }
    165
    166     public void visitConstantNameAndType(ConstantNameAndType obj) {
    167         tostring = toString(obj);
    168     }
    169
    170     public void visitConstantPool(ConstantPool obj) {
    171         tostring = toString(obj);
    172     }
    173
    174     public void visitConstantString(ConstantString obj) {
    175         tostring = toString(obj);
    176     }
    177
    178     public void visitConstantUtf8(ConstantUtf8 obj) {
    179         tostring = toString(obj);
    180     }
    181
    182     public void visitConstantValue(ConstantValue obj) {
    183         tostring = toString(obj);
    184     }
    185
    186     public void visitDeprecated(Deprecated obj) {
    187         tostring = toString(obj);
    188     }
    189
    190     public void visitExceptionTable(ExceptionTable obj) {
    191         tostring = toString(obj);
    192     }
    193
    194     public void visitField(Field obj) {
    195         tostring = toString(obj);
    196     }
    197
    198     public void visitInnerClass(InnerClass obj) {
    199         tostring = toString(obj);
    200     }
    201
    202     public void visitInnerClasses(InnerClasses obj) {
    203         tostring = toString(obj);
    204     }
    205
    206     public void visitJavaClass(JavaClass obj) {
    207         tostring = toString(obj);
    208     }
    209
    210     public void visitLineNumber(LineNumber obj) {
    211         tostring = toString(obj);
    212     }
    213
    214     public void visitLineNumberTable(LineNumberTable obj) {
    215         tostring = "<LineNumberTable: " + toString(obj) + ">";
    216     }
    217
    218     public void visitLocalVariable(LocalVariable obj) {
    219         tostring = toString(obj);
    220     }
    221
    222     public void visitLocalVariableTable(LocalVariableTable obj) {
    223         tostring = "<LocalVariableTable: " + toString(obj) + ">";
    224     }
    225
    226     public void visitMethod(Method obj) {
    227         tostring = toString(obj);
    228     }
    229
    230     public void visitSignature(Signature obj) {
    231         tostring = toString(obj);
    232     }
    233
    234     public void visitSourceFile(SourceFile obj) {
    235         tostring = toString(obj);
    236     }
    237
    238     public void visitStackMap(StackMap obj) {
    239         tostring = toString(obj);
    240     }
    241
    242     public void visitSynthetic(Synthetic obj) {
    243         tostring = toString(obj);
    244     }
    245
    246     public void visitUnknown(Unknown obj) {
    247         tostring = toString(obj);
    248     }
    249 }