Generic Method inserts.

This commit is contained in:
Michael Uhl 2019-07-26 10:18:50 +02:00
parent 809459f6e9
commit ab664efb6b

View File

@ -1,176 +1,180 @@
package typinferenzplugin; package typinferenzplugin;
import static org.eclipse.core.runtime.IStatus.ERROR; import static org.eclipse.core.runtime.IStatus.ERROR;
import static typinferenzplugin.Activator.PLUGIN_ID; import static typinferenzplugin.Activator.PLUGIN_ID;
import java.io.File; import java.io.File;
import java.io.FileNotFoundException; import java.io.FileNotFoundException;
import java.io.FileOutputStream; import java.io.FileOutputStream;
import java.io.IOException; import java.io.IOException;
import java.io.OutputStreamWriter; import java.io.OutputStreamWriter;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.Collection; import java.util.Collection;
import java.util.HashMap; import java.util.HashMap;
import java.util.HashSet; import java.util.HashSet;
import java.util.List; import java.util.List;
import java.util.Set; import java.util.Set;
import java.util.TreeSet; import java.util.TreeSet;
import java.util.Vector; import java.util.Vector;
import org.apache.commons.io.output.NullOutputStream; import org.apache.commons.io.output.NullOutputStream;
import org.eclipse.core.runtime.ILog; import org.eclipse.core.runtime.ILog;
import org.eclipse.core.runtime.Status; import org.eclipse.core.runtime.Status;
import de.dhbwstuttgart.bytecode.BytecodeGen; import de.dhbwstuttgart.bytecode.BytecodeGen;
import de.dhbwstuttgart.bytecode.Exception.BytecodeGeneratorError; import de.dhbwstuttgart.bytecode.Exception.BytecodeGeneratorError;
import de.dhbwstuttgart.bytecode.descriptor.TypeToDescriptor; import de.dhbwstuttgart.bytecode.descriptor.TypeToDescriptor;
import de.dhbwstuttgart.core.JavaTXCompiler; import de.dhbwstuttgart.bytecode.utilities.SimplifyResult;
import de.dhbwstuttgart.exceptions.TypeinferenceException; import de.dhbwstuttgart.core.JavaTXCompiler;
import de.dhbwstuttgart.syntaxtree.SourceFile; import de.dhbwstuttgart.exceptions.TypeinferenceException;
import de.dhbwstuttgart.syntaxtree.type.RefTypeOrTPHOrWildcardOrGeneric; import de.dhbwstuttgart.syntaxtree.SourceFile;
import de.dhbwstuttgart.typedeployment.TypeInsert; import de.dhbwstuttgart.syntaxtree.type.RefTypeOrTPHOrWildcardOrGeneric;
import de.dhbwstuttgart.typedeployment.TypeInsertFactory; import de.dhbwstuttgart.typedeployment.TypeInsert;
import de.dhbwstuttgart.typeinference.result.ResultSet; import de.dhbwstuttgart.typedeployment.TypeInsertFactory;
import de.dhbwstuttgart.typeinference.unify.UnifyResultListener; import de.dhbwstuttgart.typeinference.result.ResultSet;
import de.dhbwstuttgart.typeinference.unify.UnifyResultModel; import de.dhbwstuttgart.typeinference.unify.UnifyResultListener;
import typinferenzplugin.editor.JavEditor; import de.dhbwstuttgart.typeinference.unify.UnifyResultModel;
import typinferenzplugin.error.ErrorOutput; import typinferenzplugin.editor.JavEditor;
import typinferenzplugin.error.ErrorOutput;
public class Typinferenz {
public class Typinferenz {
private static final ILog LOG = Activator.getDefault().getLog();
private static final ILog LOG = Activator.getDefault().getLog();
private JavEditor editor;
private SourceFile parsedSource; private JavEditor editor;
private SourceFile parsedSource;
private JavaTXCompiler compiler;
private List<ResultSet> tiResults = new ArrayList<>(); private JavaTXCompiler compiler;
private Set<ResultSet> forByteCode = new HashSet<>(); private List<ResultSet> tiResults = new ArrayList<>();
private Set<ResultSet> forByteCode = new HashSet<>();
public Typinferenz(JavEditor forEditor) {
this.editor = forEditor; public Typinferenz(JavEditor forEditor) {
} this.editor = forEditor;
}
public UnifyResultModel run(UnifyResultListener resultListener) throws TypeinferenceException {
try { public UnifyResultModel run(UnifyResultListener resultListener) throws TypeinferenceException {
compiler = new JavaTXCompiler(editor.getFilePath().toFile(), false); try {
SourceFile parsedSourceOrNull = compiler.sourceFiles.get(editor.getFilePath().toFile()); compiler = new JavaTXCompiler(editor.getFilePath().toFile(), false);
SourceFile parsedSourceOrNull = compiler.sourceFiles.get(editor.getFilePath().toFile());
if (parsedSourceOrNull != null) {
this.parsedSource = parsedSourceOrNull; if (parsedSourceOrNull != null) {
} this.parsedSource = parsedSourceOrNull;
}
return compiler.typeInferenceAsync(resultListener, new OutputStreamWriter(new NullOutputStream()));
} catch (ClassNotFoundException e) { return compiler.typeInferenceAsync(resultListener, new OutputStreamWriter(new NullOutputStream()));
LOG.log(new Status(ERROR, PLUGIN_ID, e.getMessage(), e)); } catch (ClassNotFoundException e) {
} catch (IOException e) { LOG.log(new Status(ERROR, PLUGIN_ID, e.getMessage(), e));
LOG.log(new Status(ERROR, PLUGIN_ID, e.getMessage(), e)); } catch (IOException e) {
} LOG.log(new Status(ERROR, PLUGIN_ID, e.getMessage(), e));
}
return null;
} return null;
}
public Collection<ResultSet> getResultSets() {
return this.forByteCode; public Collection<ResultSet> getResultSets() {
} return this.forByteCode;
}
public Vector<JavMarker> updateWithResult(Vector<JavMarker> ret, List<ResultSet> newResults) {
this.tiResults.addAll(newResults); public Vector<JavMarker> updateWithResult(Vector<JavMarker> ret, List<ResultSet> newResults) {
this.forByteCode.addAll(newResults); this.tiResults.addAll(newResults);
this.forByteCode.addAll(newResults);
Set<TypeInsert> tips = new HashSet<>();
for (ResultSet tiResult : newResults) { Set<TypeInsert> tips = new HashSet<>();
tips.addAll(TypeInsertFactory.createTypeInsertPoints(parsedSource, tiResult)); String outputDirectory = getOutputDirectory();
for (TypeInsert p : tips) {
TypeReplaceMarker toAdd = new TypeReplaceMarker(editor, tiResult, p); if (this.forByteCode.size() > 0) {
if (!ret.contains(toAdd)) { for (SourceFile sf : compiler.sourceFiles.values()) {
ret.add(toAdd); try {
} else { HashMap<String, byte[]> bytecode = getBytecode(sf, this.forByteCode, outputDirectory);
//LOG.log(new Status(ERROR, PLUGIN_ID, "Marker bereits vorhanden: " + toAdd.toString())); compiler.generateBytecodForFile(outputDirectory, bytecode, sf, new ArrayList<>(forByteCode));
} this.writeClassFile(outputDirectory, bytecode);
} } catch (BytecodeGeneratorError | IOException ex) {
} ErrorMarker toAdd = new ErrorMarker(ex.getMessage(), new CodePoint(sf.getOffset()));
ret.add(toAdd);
String outputDirectory = getOutputDirectory(); }
}
if (this.forByteCode.size() > 0) { }
for (SourceFile sf : compiler.sourceFiles.values()) {
try { for (ResultSet tiResult : newResults) {
HashMap<String, byte[]> bytecode = getBytecode(sf, this.forByteCode, outputDirectory); tips.addAll(TypeInsertFactory.createTypeInsertPoints(parsedSource, tiResult));
this.writeClassFile(outputDirectory, bytecode); for (TypeInsert p : tips) {
} catch (BytecodeGeneratorError ex) { TypeReplaceMarker toAdd = new TypeReplaceMarker(editor, tiResult, p);
ErrorMarker toAdd = new ErrorMarker(ex.getMessage(), new CodePoint(sf.getOffset())); if (!ret.contains(toAdd)) {
ret.add(toAdd); ret.add(toAdd);
} } else {
} //LOG.log(new Status(ERROR, PLUGIN_ID, "Marker bereits vorhanden: " + toAdd.toString()));
} }
}
return ret; }
}
public String getOutputDirectory() { return ret;
String outputDirectory = editor.getFilePath().toString(); }
outputDirectory = outputDirectory.substring(0,
outputDirectory.length() - editor.getFilePath().lastSegment().length());// ".jav" hat Länge 4 public String getOutputDirectory() {
return outputDirectory; String outputDirectory = editor.getFilePath().toString();
} outputDirectory = outputDirectory.substring(0,
outputDirectory.length() - editor.getFilePath().lastSegment().length());// ".jav" hat Länge 4
public void updateresultSets(Vector<ResultSet> typeInsertResults) { return outputDirectory;
//this.tiResults = typeInsertResults; }
// for (ResultSet resultSet : typeInsertResults) {
// for (ResultPair<RefTypeOrTPHOrWildcardOrGeneric, RefTypeOrTPHOrWildcardOrGeneric> result : resultSet.results) { public void updateresultSets(Vector<ResultSet> typeInsertResults) {
// LOG.log(new Status(INFO, PLUGIN_ID, "Types: " + result.getRight().getClass().getCanonicalName() + "," + result.getLeft().getClass().getCanonicalName())); //this.tiResults = typeInsertResults;
// LOG.log(new Status(INFO, PLUGIN_ID, "Values: " + result.getRight() + "," + result.getLeft())); // for (ResultSet resultSet : typeInsertResults) {
// System.out.println(result.getRight() + "," + result.getLeft()); // for (ResultPair<RefTypeOrTPHOrWildcardOrGeneric, RefTypeOrTPHOrWildcardOrGeneric> result : resultSet.results) {
// } // LOG.log(new Status(INFO, PLUGIN_ID, "Types: " + result.getRight().getClass().getCanonicalName() + "," + result.getLeft().getClass().getCanonicalName()));
// } // LOG.log(new Status(INFO, PLUGIN_ID, "Values: " + result.getRight() + "," + result.getLeft()));
} // System.out.println(result.getRight() + "," + result.getLeft());
// }
public Set<String> resolve(RefTypeOrTPHOrWildcardOrGeneric tph) throws TypeinferenceException { // }
Set<String> ret = new TreeSet<>(); }
try {
for (ResultSet tiResult : tiResults) { public Set<String> resolve(RefTypeOrTPHOrWildcardOrGeneric tph) throws TypeinferenceException {
ret.add(tiResult.resolveType(tph).resolvedType.acceptTV(new TypeToDescriptor())); Set<String> ret = new TreeSet<>();
} try {
} catch (TypeinferenceException texc) { for (ResultSet tiResult : tiResults) {
throw texc; // Die aufrufende Instanz sollte daraus dann einen ErrorMarker generieren. ret.add(tiResult.resolveType(tph).resolvedType.acceptTV(new TypeToDescriptor()));
} catch (Exception exc) { }
exc.printStackTrace(); // Hier wird kein Marker generiert... nur Debug-Output } catch (TypeinferenceException texc) {
new ErrorOutput("Fehler beim Parsen und Inferieren"); throw texc; // Die aufrufende Instanz sollte daraus dann einen ErrorMarker generieren.
} } catch (Exception exc) {
exc.printStackTrace(); // Hier wird kein Marker generiert... nur Debug-Output
return ret; new ErrorOutput("Fehler beim Parsen und Inferieren");
} }
public synchronized HashMap<String, byte[]> getBytecode(SourceFile sf, Collection<ResultSet> resultSets, String path) { return ret;
HashMap<String, byte[]> classFiles = new HashMap<>(); }
BytecodeGen bytecodeGen = new BytecodeGen(classFiles, resultSets, sf, path);
bytecodeGen.visit(sf); public synchronized HashMap<String, byte[]> getBytecode(SourceFile sf, Collection<ResultSet> resultSets, String path) {
return bytecodeGen.getClassFiles(); HashMap<String, byte[]> classFiles = new HashMap<>();
} BytecodeGen bytecodeGen = new BytecodeGen(classFiles, resultSets, sf, path);
bytecodeGen.visit(sf);
public void writeClassFile(String outputDirectory, HashMap<String, byte[]> classFiles) { List<HashMap<String, SimplifyResult>> simplifyResultsList = bytecodeGen.getSimplifyResultsList();
FileOutputStream output; return bytecodeGen.getClassFiles();
for (String name : classFiles.keySet()) { }
byte[] bytecode = classFiles.get(name);
try { public void writeClassFile(String outputDirectory, HashMap<String, byte[]> classFiles) {
System.out.println("generating" + name + ".class file"); FileOutputStream output;
// output = new FileOutputStream(new File(System.getProperty("user.dir") + for (String name : classFiles.keySet()) {
// "/testBytecode/generatedBC/" +name+".class")); byte[] bytecode = classFiles.get(name);
output = new FileOutputStream(new File(outputDirectory + name + ".class")); try {
output.write(bytecode); System.out.println("generating" + name + ".class file");
output.close(); // output = new FileOutputStream(new File(System.getProperty("user.dir") +
System.out.println(name + ".class file generated"); // "/testBytecode/generatedBC/" +name+".class"));
} catch (FileNotFoundException e) { output = new FileOutputStream(new File(outputDirectory + name + ".class"));
e.printStackTrace(); output.write(bytecode);
} catch (IOException e) { output.close();
e.printStackTrace(); System.out.println(name + ".class file generated");
} } catch (FileNotFoundException e) {
} e.printStackTrace();
} catch (IOException e) {
} e.printStackTrace();
}
public SourceFile getSourceFile() { }
return parsedSource;
} }
}
public SourceFile getSourceFile() {
return parsedSource;
}
}