
com.ibm.wala.shrike.shrikeBT.shrikeCT.CTUtils Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of com.ibm.wala.shrike Show documentation
Show all versions of com.ibm.wala.shrike Show documentation
T. J. Watson Libraries for Analysis
The newest version!
/*
* Copyright (c) 2002,2006 IBM Corporation.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
* IBM Corporation - initial API and implementation
*/
package com.ibm.wala.shrike.shrikeBT.shrikeCT;
import com.ibm.wala.shrike.shrikeBT.Constants;
import com.ibm.wala.shrike.shrikeBT.MethodData;
import com.ibm.wala.shrike.shrikeBT.analysis.ClassHierarchyStore;
import com.ibm.wala.shrike.shrikeCT.ClassReader;
import com.ibm.wala.shrike.shrikeCT.ClassWriter;
import com.ibm.wala.shrike.shrikeCT.ClassWriter.Element;
import com.ibm.wala.shrike.shrikeCT.CodeWriter;
import com.ibm.wala.shrike.shrikeCT.InvalidClassFileException;
import com.ibm.wala.shrike.shrikeCT.LineNumberTableWriter;
import java.util.Arrays;
/**
* This is a dumping ground for useful functions that manipulate class info.
*
* @author [email protected]
*/
public class CTUtils {
public static void addClassToHierarchy(ClassHierarchyStore store, ClassReader cr)
throws InvalidClassFileException, IllegalArgumentException {
if (store == null) {
throw new IllegalArgumentException("store is null");
}
if (cr == null) {
throw new IllegalArgumentException();
}
String[] superInterfaces = new String[cr.getInterfaceCount()];
for (int i = 0; i < superInterfaces.length; i++) {
superInterfaces[i] = CTDecoder.convertClassToType(cr.getInterfaceName(i));
}
String superName = cr.getSuperName();
if ("java/io/File".equals(cr.getName()) || "java/lang/Throwable".equals(cr.getName())) {
System.err.println(superName);
}
store.setClassInfo(
CTDecoder.convertClassToType(cr.getName()),
(cr.getAccessFlags() & Constants.ACC_INTERFACE) != 0,
(cr.getAccessFlags() & Constants.ACC_FINAL) != 0,
superName != null ? CTDecoder.convertClassToType(superName) : null,
superInterfaces);
}
/**
* Compile and add a method to a {@link ClassWriter}.
*
* @param md the method data
* @param classWriter the target class writer
* @param rawLines line number information if available, otherwise {@code null}
*/
public static void compileAndAddMethodToClassWriter(
MethodData md, ClassWriter classWriter, ClassWriter.Element rawLines) {
if (classWriter == null) {
throw new IllegalArgumentException("classWriter is null");
}
if (md == null) {
throw new IllegalArgumentException("md is null");
}
CTCompiler compiler = CTCompiler.make(classWriter, md);
compiler.compile();
CTCompiler.Output output = compiler.getOutput();
CodeWriter code = new CodeWriter(classWriter);
code.setMaxStack(output.getMaxStack());
code.setMaxLocals(output.getMaxLocals());
code.setCode(output.getCode());
code.setRawHandlers(output.getRawHandlers());
LineNumberTableWriter lines = null;
// I guess it is the line numbers in the java files.
if (rawLines == null) {
// add fake line numbers: just map each bytecode instruction to its own
// 'line'
// NOTE:Should not use md.getInstructions().length, because the
// the length of the created code can be smaller than the md's instruction
// length
// WRONG: int[] newLineMap = new int[md.getInstructions().length];
int[] newLineMap = new int[code.getCodeLength()];
Arrays.setAll(newLineMap, i -> i);
int[] rawTable = LineNumberTableWriter.makeRawTable(newLineMap);
lines = new LineNumberTableWriter(classWriter);
lines.setRawTable(rawTable);
}
code.setAttributes(new ClassWriter.Element[] {rawLines == null ? lines : rawLines});
Element[] elements = {code};
// System.out.println("Name:"+md.getName()+" Sig:"+md.getSignature());
classWriter.addMethod(md.getAccess(), md.getName(), md.getSignature(), elements);
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy