00001 package ca.mcgill.sable.soot;
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00067
00068
00069
00070
00071
00072
00073
00074
00075
00076
00077
00078 import ca.mcgill.sable.util.*;
00079 import ca.mcgill.sable.soot.baf.*;
00080
00081 public class SootMethod
00082 {
00083 String name;
00084 List parameterTypes;
00085 Type returnType;
00086
00087 boolean isDeclared;
00088 SootClass declaringClass;
00089
00090 int modifiers;
00091
00092 List exceptions = new ArrayList();
00093
00094 Map repToBody = new HashMap();
00095
00096
00097
00098
00099
00100 public ca.mcgill.sable.soot.coffi.ClassFile coffiClass;
00101
00102
00103
00104
00105
00106 public ca.mcgill.sable.soot.coffi.method_info coffiMethod;
00107
00108
00109 public SootMethod(String name, List parameterTypes, Type returnType)
00110 {
00111 this.name = name;
00112 this.parameterTypes = new ArrayList();
00113 this.parameterTypes.addAll(parameterTypes);
00114 this.returnType = returnType;
00115 }
00116 public SootMethod(String name, List parameterTypes, Type returnType, int modifiers)
00117 {
00118 this.name = name;
00119 this.parameterTypes = new ArrayList();
00120 this.parameterTypes.addAll(parameterTypes);
00121
00122 this.returnType = returnType;
00123 this.modifiers = modifiers;
00124 }
00125
00126
00127
00128
00129
00130
00131
00132
00133
00134
00135
00136
00137
00138
00139
00140
00141
00142
00143 public void addException(SootClass e) throws AlreadyThrowsException
00144 {
00145 if(exceptions.contains(e))
00146 throw new AlreadyThrowsException(e.getName());
00147
00148 exceptions.add(e);
00149 }
00150
00151
00152
00153
00154 public Body getBody(BodyRepresentation bodyRep)
00155 {
00156 if(bodyRep.equals(ClassFile.v()))
00157 return new ClassFileBody(this);
00158 else if(repToBody.containsKey(bodyRep))
00159 return (Body) repToBody.get(bodyRep);
00160 else
00161 throw new RuntimeException("Method does not have a stored representation for" + bodyRep);
00162 }
00163
00164
00165
00166
00167
00168 public String getDeclaration()
00169 {
00170 StringBuffer buffer = new StringBuffer();
00171
00172 buffer.append(Modifier.toString(this.getModifiers()));
00173
00174 if(buffer.length() != 0)
00175 buffer.append(" ");
00176
00177 buffer.append(this.getReturnType().toString() + " " + this.getName());
00178 buffer.append("(");
00179
00180 Iterator typeIt = this.getParameterTypes().iterator();
00181
00182 if(typeIt.hasNext())
00183 {
00184 buffer.append(typeIt.next());
00185
00186 while(typeIt.hasNext())
00187 {
00188 buffer.append(", ");
00189 buffer.append(typeIt.next());
00190 }
00191 }
00192
00193 buffer.append(")");
00194
00195
00196 {
00197 Iterator exceptionIt = this.getExceptions().iterator();
00198
00199 if(exceptionIt.hasNext())
00200 {
00201 buffer.append(" throws ");
00202 buffer.append(((SootClass) exceptionIt.next()).getName());
00203
00204 while(exceptionIt.hasNext())
00205 {
00206 buffer.append(", ");
00207 buffer.append(((SootClass) exceptionIt.next()).getName());
00208 }
00209 }
00210
00211 }
00212
00213 return buffer.toString();
00214 }
00215 public SootClass getDeclaringClass() throws NotDeclaredException
00216 {
00217 if(!isDeclared)
00218 throw new NotDeclaredException(getName());
00219
00220 return declaringClass;
00221 }
00222
00223
00224
00225
00226 public List getExceptions()
00227 {
00228 return exceptions;
00229 }
00230 public int getModifiers()
00231 {
00232 return modifiers;
00233 }
00234 public String getName()
00235 {
00236 return name;
00237 }
00238 public int getParameterCount()
00239 {
00240 return parameterTypes.size();
00241 }
00242 public Type getParameterType(int n)
00243 {
00244 return (Type) parameterTypes.get(n);
00245 }
00246
00247
00248
00249
00250 public List getParameterTypes()
00251 {
00252 return parameterTypes;
00253 }
00254 public Type getReturnType()
00255 {
00256 return returnType;
00257 }
00258
00259
00260
00261
00262 public String getSignature()
00263 {
00264 StringBuffer buffer = new StringBuffer();
00265
00266 buffer.append(getDeclaringClass().getName());
00267 buffer.append(".");
00268 buffer.append(getName());
00269 buffer.append("(");
00270
00271 Iterator typeIt = getParameterTypes().iterator();
00272
00273 if(typeIt.hasNext())
00274 {
00275 buffer.append(typeIt.next());
00276
00277 while(typeIt.hasNext())
00278 {
00279 buffer.append(",");
00280 buffer.append(typeIt.next());
00281 }
00282 }
00283
00284 buffer.append(")");
00285
00286 buffer.append(":" + getReturnType().toString());
00287
00288 return buffer.toString();
00289 }
00290
00291
00292
00293
00294 public boolean isBodyStored(BodyRepresentation bodyRep)
00295 {
00296 return repToBody.containsKey(bodyRep);
00297 }
00298 public boolean isDeclared()
00299 {
00300 return isDeclared;
00301 }
00302
00303
00304
00305
00306 public boolean isStatic()
00307 {
00308 return Modifier.isStatic(this.getModifiers());
00309 }
00310 public void removeException(SootClass e) throws DoesNotThrowException
00311 {
00312 if(!exceptions.contains(e))
00313 throw new DoesNotThrowException(e.getName());
00314 }
00315 public void setModifiers(int modifiers)
00316 {
00317 this.modifiers = modifiers;
00318 }
00319 public void setName(String name)
00320 {
00321 this.name = name;
00322 }
00323 public void setParameterTypes(List parameterTypes)
00324 {
00325 this.parameterTypes = new ArrayList();
00326 this.parameterTypes.addAll(parameterTypes);
00327 }
00328 public void setReturnType(Type t)
00329 {
00330 returnType = t;
00331 }
00332
00333
00334
00335
00336
00337
00338
00339
00340
00341
00342
00343
00344
00345
00346
00347
00348
00349
00350
00351
00352
00353
00354
00355
00356
00357 public void setSource(ca.mcgill.sable.soot.coffi.ClassFile coffiClass,
00358 ca.mcgill.sable.soot.coffi.method_info coffiMethod)
00359 {
00360 this.coffiClass = coffiClass;
00361 this.coffiMethod = coffiMethod;
00362 }
00363
00364
00365
00366
00367 public void storeBody(BodyRepresentation r, Body b)
00368 {
00369 repToBody.put(r, b);
00370 }
00371 public boolean throwsException(SootClass e)
00372 {
00373 return exceptions.contains(e);
00374 }
00375 public String toString()
00376 {
00377 return getSignature();
00378 }
00379 }