001: /*
002: * Copyright (c) 2001-2007, Jean Tessier
003: * All rights reserved.
004: *
005: * Redistribution and use in source and binary forms, with or without
006: * modification, are permitted provided that the following conditions
007: * are met:
008: *
009: * * Redistributions of source code must retain the above copyright
010: * notice, this list of conditions and the following disclaimer.
011: *
012: * * Redistributions in binary form must reproduce the above copyright
013: * notice, this list of conditions and the following disclaimer in the
014: * documentation and/or other materials provided with the distribution.
015: *
016: * * Neither the name of Jean Tessier nor the names of his contributors
017: * may be used to endorse or promote products derived from this software
018: * without specific prior written permission.
019: *
020: * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
021: * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
022: * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
023: * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR
024: * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
025: * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
026: * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
027: * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
028: * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
029: * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
030: * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
031: */
032:
033: package com.jeantessier.classreader;
034:
035: import java.util.*;
036:
037: import org.apache.log4j.*;
038: import org.apache.oro.text.perl.*;
039:
040: public final class SignatureHelper {
041: private static final Perl5Util perl = new Perl5Util();
042:
043: private static Map<String, String> conversion = new HashMap<String, String>();
044:
045: static {
046: conversion.put("B", "byte");
047: conversion.put("C", "char");
048: conversion.put("D", "double");
049: conversion.put("F", "float");
050: conversion.put("I", "int");
051: conversion.put("J", "long");
052: conversion.put("S", "short");
053: conversion.put("V", "void");
054: conversion.put("Z", "boolean");
055: }
056:
057: public static String convert(String type) {
058: String result = null;
059:
060: Logger.getLogger(SignatureHelper.class).debug(
061: "Begin Convert(\"" + type + "\")");
062:
063: if (type.length() == 1) {
064: result = conversion.get(type);
065: } else if (type.charAt(0) == 'L') {
066: result = path2ClassName(type
067: .substring(1, type.indexOf(';')));
068: } else if (type.charAt(0) == '[') {
069: result = convert(type.substring(1)) + "[]";
070: }
071:
072: Logger.getLogger(SignatureHelper.class).debug(
073: "End Convert(\"" + type + "\"): \"" + result + "\"");
074:
075: return result;
076: }
077:
078: public static String convertClassName(String type) {
079: String result;
080:
081: if (type.charAt(0) == 'L' && type.indexOf(';') > 0) {
082: result = path2ClassName(type
083: .substring(1, type.indexOf(';')));
084: } else if (type.charAt(0) == '[') {
085: result = convert(type.substring(1)) + "[]";
086: } else {
087: result = path2ClassName(type);
088: }
089:
090: return result;
091: }
092:
093: public static String path2ClassName(String path) {
094: return perl.substitute("s/\\//./g", path);
095: }
096:
097: public static String getSignature(String descriptor) {
098: StringBuffer result = new StringBuffer();
099:
100: Logger.getLogger(SignatureHelper.class).debug(
101: "Begin Signature(\"" + descriptor + "\")");
102:
103: result.append("(");
104:
105: int start = descriptor.indexOf("(") + 1;
106: int end = descriptor.indexOf(")");
107:
108: SignatureIterator i = new SignatureIterator(descriptor
109: .substring(start, end));
110: while (i.hasNext()) {
111: result.append(i.next());
112: if (i.hasNext()) {
113: result.append(", ");
114: }
115: }
116:
117: result.append(")");
118:
119: Logger.getLogger(SignatureHelper.class).debug(
120: "End Signature(\"" + descriptor + "\"): \"" + result
121: + "\"");
122:
123: return result.toString();
124: }
125:
126: public static int getParameterCount(String descriptor) {
127: int result = 0;
128:
129: Logger.getLogger(SignatureHelper.class).debug(
130: "Begin ParameterCount(\"" + descriptor + "\")");
131:
132: int start = descriptor.indexOf("(") + 1;
133: int end = descriptor.indexOf(")");
134:
135: SignatureIterator i = new SignatureIterator(descriptor
136: .substring(start, end));
137: while (i.hasNext()) {
138: i.next();
139: result++;
140: }
141:
142: Logger.getLogger(SignatureHelper.class).debug(
143: "End ParameterCount(\"" + descriptor + "\"): \""
144: + result + "\"");
145:
146: return result;
147: }
148:
149: public static String getReturnType(String descriptor) {
150: return convert(descriptor
151: .substring(descriptor.lastIndexOf(")") + 1));
152: }
153:
154: public static String getType(String descriptor) {
155: return convert(descriptor);
156: }
157: }
158:
159: class SignatureIterator implements Iterator {
160: private String descriptor;
161: private int currentPos = 0;
162:
163: public SignatureIterator(String descriptor) {
164: this .descriptor = descriptor;
165: }
166:
167: public boolean hasNext() {
168: return currentPos < descriptor.length();
169: }
170:
171: public Object next() {
172: String result;
173:
174: if (hasNext()) {
175: int nextPos = currentPos;
176:
177: while (descriptor.charAt(nextPos) == '[') {
178: nextPos++;
179: }
180:
181: if (descriptor.charAt(nextPos) == 'L') {
182: nextPos = descriptor.indexOf(";", nextPos);
183: }
184:
185: result = SignatureHelper.convert(descriptor.substring(
186: currentPos, nextPos + 1));
187:
188: currentPos = nextPos + 1;
189: } else {
190: throw new NoSuchElementException();
191: }
192:
193: return result;
194: }
195:
196: public void remove() {
197: throw new UnsupportedOperationException();
198: }
199: }
|