Compare commits

..

64 Commits

Author SHA1 Message Date
NoName11234
588036ea46 removed unused code 2024-03-15 15:49:15 +01:00
NoName11234
70b28bbfb0 removed debug variables 2024-03-15 14:54:14 +01:00
NoName11234
701962b0e7 code cleanup 2024-03-15 14:15:41 +01:00
NoName11234
e91a9370df removed threadcounter from TypeUnifyTask 2024-03-07 19:18:54 +01:00
NoName11234
d71e67cfdd Merge branch 'parallelUnifyResultModel' into unif23NoOptParallel_Lehmann 2024-02-21 18:10:03 +01:00
NoName11234
c2c2d6f445 implemented UnifyResultModelParallel in UnifyTest 2024-02-19 17:59:21 +01:00
NoName11234
7296e3de44 implemented UnifyResultModelParallel 2024-02-19 17:58:52 +01:00
NoName11234
c1aebaf1f5 implemented new class UnifyResultModelParallel 2024-02-19 17:27:16 +01:00
NoName11234
2871586c71 removed usesless variance in test 2024-02-06 18:39:44 +01:00
NoName11234
fa1f3a0507 removed unused statement 2024-02-05 19:39:36 +01:00
NoName11234
f66edd4c4b renamed helper methods 2024-02-05 19:27:06 +01:00
NoName11234
598fe8ebe9 renamed unify tests 2024-02-05 19:25:08 +01:00
NoName11234
41d97dfa80 Merge branch 'unif23NoOptParallel_Lehmann' of https://gitea.hb.dhbw-stuttgart.de/i21017/JavaCompilerCore into unif23NoOptParallel_Lehmann 2024-02-04 13:31:05 +01:00
NoName11234
0f18cedf90 implemented succesfully running test 2024-02-04 13:28:01 +01:00
f43d1f4f4f Merge pull request 'Update src/test/java/typeinference/UnifyTest.java' (#1) from stan-patch-Finite-Closure into unif23NoOptParallel_Lehmann
Reviewed-on: i21017/JavaCompilerCore#1
2024-02-04 12:03:32 +00:00
2a44773403 Update src/test/java/typeinference/UnifyTest.java
Die "Smaller" Relationen waren in falscher Richtung.
Außerdem müssen TypeParams bei List und AbstractList angefügt werden
2024-02-01 12:06:10 +00:00
NoName11234
a6ca31d509 changed UnifyTaskModel to UnifyTaskModelParallel 2024-01-30 19:37:47 +01:00
NoName11234
b13f2b357b removed old UnifyTaskModel from TypeUnify and TypeUnifyTask 2024-01-29 20:03:55 +01:00
NoName11234
45fa0ff0b9 added class for terminating calculations 2024-01-28 13:39:47 +01:00
NoName11234
c292ff2d9e added non-threaded close() method for logging 2024-01-25 20:08:32 +01:00
NoName11234
c14dd6e97c added support for non-threaded logging to WriterActiveObject 2024-01-25 19:55:56 +01:00
NoName11234
8f8ee9a385 fixed bug where constraints in test had undefinded placeholder 2024-01-24 22:20:13 +01:00
NoName11234
3863968a6e added smallest unify test possible 2024-01-23 18:59:39 +01:00
NoName11234
03c432455d fixed bug where statisticsFile was not initialized when using one of the constructors of TypeUnifyTask 2024-01-23 18:58:59 +01:00
NoName11234
441e50a70d removed useless synchronized-blocks and concenated multiple writes to logfile 2024-01-23 17:57:07 +01:00
NoName11234
0807885465 WriterActiveObject now uses same forkjointhreadpool as tasks 2024-01-21 22:16:35 +01:00
NoName11234
8abe7f6c28 updated classes to use WriterActiveObject for logging 2024-01-21 14:21:43 +01:00
NoName11234
2a92a0e48e added function for closing file to WriterActiveObject 2024-01-21 13:41:21 +01:00
NoName11234
b3639a3d08 removed synchronized(this) from TypeUnifyTask constructor 2024-01-20 23:23:08 +01:00
NoName11234
28969e7931 added class for thread safe writing in logfiles 2024-01-20 23:01:21 +01:00
NoName11234
b806fa88ff removed synchronized-block from writeLog() and writeStatistics() in TypeUnifyTask 2024-01-18 21:21:42 +01:00
NoName11234
301e9143ec changed output of unifyTest() 2024-01-18 21:20:48 +01:00
NoName11234
bb4eaaccc5 implemented unify test 2024-01-18 18:29:36 +01:00
NoName11234
4dbae46765 implemented list of UnifyPairs in test unifyTest() 2024-01-16 19:23:19 +01:00
NoName11234
c64071f235 Revert "added resources for tests"
This reverts commit 5aadb7545e.
2024-01-16 18:29:37 +01:00
NoName11234
94dbf1f7ad Revert "added resource files for testing"
This reverts commit 890f64c813.
2024-01-16 18:27:59 +01:00
NoName11234
890f64c813 added resource files for testing 2023-12-26 17:47:18 +01:00
NoName11234
5aadb7545e added resources for tests 2023-12-26 17:28:08 +01:00
NoName11234
0c0ac61a02 changed outputstream for debugging to NullOutputStream 2023-12-26 16:59:37 +01:00
NoName11234
46192e3fd3 changed java version from 19 to 21 2023-12-26 16:45:35 +01:00
pl@gohorb.ba-horb.de
61653c5d88 modified: src/main/java/de/dhbwstuttgart/typeinference/unify/TypeUnifyTask.java 2023-05-25 10:05:10 +02:00
pl@gohorb.ba-horb.de
3cd608a4ac modified: src/main/java/de/dhbwstuttgart/typeinference/unify/TypeUnify.java
modified:   src/main/java/de/dhbwstuttgart/typeinference/unify/TypeUnifyTask.java
2023-05-15 16:56:04 +02:00
pl@gohorb.ba-horb.de
deec0ae706 Start branch unif23NoOptParallel
modified:   Makefile
	modified:   src/main/java/de/dhbwstuttgart/core/JavaTXCompiler.java
	modified:   src/main/java/de/dhbwstuttgart/typeinference/unify/TypeUnifyTask.java
2023-04-24 17:18:45 +02:00
pl@gohorb.ba-horb.de
d6a79ea3a1 modified: src/main/java/de/dhbwstuttgart/typeinference/unify/TypeUnifyTask.java 2023-04-11 22:45:15 +02:00
pl@gohorb.ba-horb.de
1f909f13ee modified: src/main/java/de/dhbwstuttgart/typeinference/unify/TypeUnifyTask.java 2023-04-11 18:01:44 +02:00
pl@gohorb.ba-horb.de
be6f4bd578 Merge remote-tracking branch 'origin/targetBytecode' into unif23 2023-04-11 15:52:26 +02:00
pl@gohorb.ba-horb.de
478efd5649 Merge branch 'unif23' of ssh://gohorb.ba-horb.de/bahome/projekt/git/JavaCompilerCore into unif23 2023-04-11 15:40:27 +02:00
pl@gohorb.ba-horb.de
c73e57cf2b new file: resources/bytecode/javFiles/Scalar.jav 2023-04-11 15:35:15 +02:00
pl@gohorb.ba-horb.de
ce29f4bcf1 Merge branch 'unif23' of ssh://gohorb.ba-horb.de/bahome/projekt/git/JavaCompilerCore into Unif23
Conflicts:
	src/test/java/targetast/TestComplete.java
2023-04-10 22:14:46 +02:00
pl@gohorb.ba-horb.de
42821f3215 modified: src/main/java/de/dhbwstuttgart/typeinference/unify/RuleSet.java
modified:   src/test/java/targetast/TestComplete.java
2023-04-10 22:07:47 +02:00
pl@gohorb.ba-horb.de
f68afc88a6 modified: src/main/java/de/dhbwstuttgart/typeinference/unify/TypeUnifyTask.java 2023-04-06 17:58:32 +02:00
pl@gohorb.ba-horb.de
82061474b2 modified: resources/bytecode/javFiles/Scalar.jav
modified:   src/main/java/de/dhbwstuttgart/typeinference/typeAlgo/TYPEStmt.java
2023-04-04 17:26:13 +02:00
pl@gohorb.ba-horb.de
d849bc127f Merge remote-tracking branch 'origin/targetBytecode' into unif23 2023-04-04 16:47:19 +02:00
pl@gohorb.ba-horb.de
6815d8fc0a modified: Makefile
modified:   src/main/java/de/dhbwstuttgart/typeinference/unify/TypeUnifyTask.java
2023-03-31 17:58:02 +02:00
pl@gohorb.ba-horb.de
317f8b1aad new file: Makefile
deleted:    Test.java
	modified:   src/main/java/de/dhbwstuttgart/typeinference/unify/TypeUnifyTask.java
2023-03-31 15:54:17 +02:00
pl@gohorb.ba-horb.de
79335449d0 modified: src/main/java/de/dhbwstuttgart/typeinference/unify/TypeUnifyTask.java
Statistics fertig (Version 1)
2023-03-23 12:00:04 +01:00
pl@gohorb.ba-horb.de
14606a846e modified: src/main/java/de/dhbwstuttgart/core/JavaTXCompiler.java
modified:   src/main/java/de/dhbwstuttgart/typeinference/unify/TypeUnify.java
	modified:   src/main/java/de/dhbwstuttgart/typeinference/unify/TypeUnify2Task.java
	modified:   src/main/java/de/dhbwstuttgart/typeinference/unify/TypeUnifyTask.java
2023-03-22 19:01:36 +01:00
2b67230a15 Consider public and standard constructors ones 2023-03-21 16:31:45 +01:00
pl@gohorb.ba-horb.de
29b05b56cc Merge branch 'targetBytecode' into unif23 2023-03-21 16:29:14 +01:00
pl@gohorb.ba-horb.de
08b9fc0ea3 modified: src/main/java/de/dhbwstuttgart/core/JavaTXCompiler.java
statistics eingefuegt
2023-03-21 16:23:18 +01:00
pl@gohorb.ba-horb.de
070dd16999 modified: src/main/java/de/dhbwstuttgart/typeinference/typeAlgo/TYPEStmt.java 2023-03-21 10:30:13 +01:00
pl@gohorb.ba-horb.de
9d7e46925d modified: src/main/java/de/dhbwstuttgart/typeinference/typeAlgo/TYPEStmt.java 2023-03-21 10:26:55 +01:00
pl@gohorb.ba-horb.de
d780d322f0 modified: src/main/java/de/dhbwstuttgart/core/JavaTXCompiler.java
modified:   src/main/java/de/dhbwstuttgart/typeinference/typeAlgo/TYPEStmt.java
2023-03-20 18:33:58 +01:00
pl@gohorb.ba-horb.de
867f3d39e8 modified: src/main/java/de/dhbwstuttgart/typeinference/unify/TypeUnifyTask.java
modified:   src/test/java/targetast/TestComplete.java
2023-03-20 16:05:28 +01:00
31 changed files with 1920 additions and 3189 deletions

3
Makefile Normal file
View File

@@ -0,0 +1,3 @@
NoOptParallel:
mvn -DskipTests package
cp target/JavaTXcompiler-0.1-jar-with-dependencies.jar target/JavaTXcompiler-0.1-jar-with-dependencies_NoOptParallel.jar

View File

@@ -54,8 +54,8 @@ http://maven.apache.org/maven-v4_0_0.xsd">
<version>3.8.0</version>
<configuration>
<compilerArgs>--enable-preview</compilerArgs>
<source>19</source>
<target>19</target>
<source>21</source>
<target>21</target>
</configuration>
</plugin>
<plugin>

View File

@@ -1,4 +1,4 @@
import java.util.Vector;
//import java.util.Vector;
import java.lang.Integer;
import java.lang.Float;
//import java.lang.Byte;
@@ -6,21 +6,11 @@ import java.lang.Float;
public class Scalar extends Vector<Integer> {
Scalar(v) {
Integer i;
i = 0;
while(i < v.size()) {
this.add(v.elementAt(i));
i=i+1;
}
}
mul(v) {
var ret = 0;
var i = 0;
while(i < size()) {
ret = ret + this.elementAt(i) * v.elementAt(i);
i = i+1;
}
return ret;
}

View File

@@ -1,11 +0,0 @@
import java.lang.String;
class TXGenerics {
a;
b;
test() {
var c = new Cycle();
c.m(a, b);
}
}

View File

@@ -5,7 +5,7 @@ public class TestContraVariant {
x = y;
return y;
}
main(x) {
return m(x);
}

View File

@@ -1,12 +1,10 @@
public class TestTwoCalls {
// <O> O -> O
id(b) {
var c = b;
return c;
}
// <T, S> (S, T) -> T
main(x,y) {
id(x);
return id(y);

View File

@@ -1000,7 +1000,7 @@ public class Codegen {
private void generateConstructor(TargetConstructor constructor) {
MethodVisitor mv = cw.visitMethod(constructor.access() | ACC_PUBLIC, "<init>", constructor.getDescriptor(), constructor.getSignature(), null);
if (constructor.txGenerics() != null)
mv.visitAttribute(new JavaTXSignatureAttribute(constructor.getTXSignature()));
mv.visitAttribute(new JavaTXSignatureAttribute(cw.newConst(constructor.getTXSignature())));
mv.visitCode();
var state = new State(null, mv, 1);
@@ -1027,7 +1027,7 @@ public class Codegen {
// TODO The older codegen has set ACC_PUBLIC for all methods, good for testing but bad for everything else
MethodVisitor mv = cw.visitMethod(method.access() | ACC_PUBLIC, method.name(), method.getDescriptor(), method.getSignature(), null);
if (method.txSignature() != null) {
mv.visitAttribute(new JavaTXSignatureAttribute(method.getTXSignature()));
mv.visitAttribute(new JavaTXSignatureAttribute(cw.newConst(method.getTXSignature())));
}
System.out.println(method.getDescriptor());
@@ -1044,14 +1044,11 @@ public class Codegen {
}
private static String generateSignature(TargetClass clazz, Set<TargetGeneric> generics) {
String ret = "";
if (generics.size() > 0) {
ret += "<";
for (var generic : generics) {
ret += generic.name() + ":" + generic.bound().toDescriptor();
}
ret += ">";
String ret = "<";
for (var generic : generics) {
ret += generic.name() + ":" + generic.bound().toDescriptor();
}
ret += ">";
ret += clazz.superType().toDescriptor();
return ret;
@@ -1063,7 +1060,7 @@ public class Codegen {
clazz.implementingInterfaces().stream().map(TargetType::toSignature).toArray(String[]::new)
);
if (clazz.txGenerics() != null)
cw.visitAttribute(new JavaTXSignatureAttribute(generateSignature(clazz, clazz.txGenerics())));
cw.visitAttribute(new JavaTXSignatureAttribute(cw.newConst(generateSignature(clazz, clazz.txGenerics()))));
clazz.fields().forEach(this::generateField);
clazz.constructors().forEach(this::generateConstructor);

View File

@@ -3,13 +3,10 @@ package de.dhbwstuttgart.bytecode;
import org.objectweb.asm.*;
public class JavaTXSignatureAttribute extends Attribute {
public String signature;
final int signature;
public JavaTXSignatureAttribute() {
protected JavaTXSignatureAttribute(int signature) {
super("JavaTXSignature");
}
protected JavaTXSignatureAttribute(String signature) {
this();
this.signature = signature;
}
@@ -17,14 +14,13 @@ public class JavaTXSignatureAttribute extends Attribute {
protected Attribute read(ClassReader classReader, int offset, int length, char[] charBuffer, int codeAttributeOffset, Label[] labels) {
var data = new byte[length];
System.arraycopy(classReader.b, offset, data, 0, length);
var constantPoolOffset = data[0] << 8 | data[1];
return new JavaTXSignatureAttribute((String) classReader.readConst(constantPoolOffset, charBuffer));
return new JavaTXSignatureAttribute(data[0] << 8 | data[1]);
}
@Override
protected ByteVector write(ClassWriter classWriter, byte[] code, int codeLength, int maxStack, int maxLocals) {
var data = new ByteVector();
data.putShort(classWriter.newConst(this.signature));
data.putShort(this.signature);
return data;
}
}

View File

@@ -37,20 +37,13 @@ import de.dhbwstuttgart.typeinference.constraints.ConstraintSet;
import de.dhbwstuttgart.typeinference.constraints.Pair;
import de.dhbwstuttgart.typeinference.result.ResultSet;
import de.dhbwstuttgart.typeinference.typeAlgo.TYPE;
import de.dhbwstuttgart.typeinference.unify.RuleSet;
import de.dhbwstuttgart.typeinference.unify.TypeUnify;
import de.dhbwstuttgart.typeinference.unify.distributeVariance;
import de.dhbwstuttgart.typeinference.unify.*;
import de.dhbwstuttgart.typeinference.unify.interfaces.IFiniteClosure;
import de.dhbwstuttgart.typeinference.unify.model.PairOperator;
import de.dhbwstuttgart.typeinference.unify.model.PlaceholderType;
import de.dhbwstuttgart.typeinference.unify.model.UnifyPair;
import de.dhbwstuttgart.typeinference.unify.model.UnifyType;
import de.dhbwstuttgart.util.BiRelation;
import de.dhbwstuttgart.typeinference.unify.TypeUnifyTask;
import de.dhbwstuttgart.typeinference.unify.UnifyResultListener;
import de.dhbwstuttgart.typeinference.unify.UnifyResultListenerImpl;
import de.dhbwstuttgart.typeinference.unify.UnifyResultModel;
import de.dhbwstuttgart.typeinference.unify.UnifyTaskModel;
import java.io.File;
import java.io.FileOutputStream;
@@ -58,6 +51,7 @@ import java.io.FileWriter;
import java.io.IOException;
import java.io.OutputStreamWriter;
import java.io.Writer;
import java.sql.Timestamp;
import java.util.*;
import java.util.function.Function;
import java.util.stream.Collectors;
@@ -69,11 +63,12 @@ public class JavaTXCompiler {
//public static JavaTXCompiler INSTANCE;
final CompilationEnvironment environment;
Boolean resultmodel = false;
Boolean resultmodel = true;
public final Map<File, SourceFile> sourceFiles = new HashMap<>();
Boolean log = false; //gibt an ob ein Log-File nach System.getProperty("user.dir")+""/logFiles/"" geschrieben werden soll?
public volatile UnifyTaskModel usedTasks = new UnifyTaskModel();
public UnifyTaskModelParallel usedTasks = new UnifyTaskModelParallel();
private final DirectoryClassLoader classLoader;
static Writer statistics;
public JavaTXCompiler(File sourceFile) throws IOException, ClassNotFoundException {
this(Arrays.asList(sourceFile), null);
@@ -86,6 +81,9 @@ public class JavaTXCompiler {
this(sourceFiles, null);
}
public JavaTXCompiler(List<File> sources, List<File> contextPath) throws IOException, ClassNotFoundException {
//statistics = new FileWriter(new File(System.getProperty("user.dir") + "/" + sources.get(0).getName() + "_"+ new Timestamp(System.currentTimeMillis())));
statistics = new OutputStreamWriter(new NullOutputStream());
statistics.write("test");
if(contextPath == null || contextPath.isEmpty()){
//When no contextPaths are given, the working directory is the sources root
contextPath = Lists.newArrayList(new File(System.getProperty("user.dir")));
@@ -371,7 +369,7 @@ public class JavaTXCompiler {
* }
*/
public UnifyResultModel typeInferenceAsync(UnifyResultListener resultListener, Writer logFile)
public UnifyResultModelParallel typeInferenceAsync(UnifyResultListener resultListener, Writer logFile)
throws ClassNotFoundException, IOException {
List<ClassOrInterface> allClasses = new ArrayList<>();// environment.getAllAvailableClasses();
// Alle Importierten Klassen in allen geparsten Sourcefiles kommen ins FC
@@ -384,7 +382,7 @@ public class JavaTXCompiler {
final ConstraintSet<Pair> cons = getConstraints();
Set<Set<UnifyPair>> results = new HashSet<>();
UnifyResultModel urm = null;
UnifyResultModelParallel urm = null;
// urm.addUnifyResultListener(resultListener);
try {
logFile = logFile == null
@@ -392,7 +390,7 @@ public class JavaTXCompiler {
: logFile;
IFiniteClosure finiteClosure = UnifyTypeFactory.generateFC(allClasses, logFile, classLoader);
System.out.println(finiteClosure);
urm = new UnifyResultModel(cons, finiteClosure);
urm = new UnifyResultModelParallel(cons, finiteClosure);
urm.addUnifyResultListener(resultListener);
ConstraintSet<UnifyPair> unifyCons = UnifyTypeFactory.convert(cons);
@@ -578,6 +576,7 @@ public class JavaTXCompiler {
unifyCons = unifyCons.map(distributeInnerVars);
logFile.write("\nUnify_distributeInnerVars: " + unifyCons.toString());
TypeUnify unify = new TypeUnify();
unify.statistics = statistics;
// Set<Set<UnifyPair>> results = new HashSet<>(); Nach vorne gezogen
logFile.write("FC:\\" + finiteClosure.toString() + "\n");
for (SourceFile sf : this.sourceFiles.values()) {
@@ -721,7 +720,7 @@ public class JavaTXCompiler {
}).collect(Collectors.toCollection(ArrayList::new))*/;
if (resultmodel) {
/* UnifyResultModel Anfang */
UnifyResultModel urm = new UnifyResultModel(cons, finiteClosure);
UnifyResultModelParallel urm = new UnifyResultModelParallel(cons, finiteClosure);
UnifyResultListenerImpl li = new UnifyResultListenerImpl();
urm.addUnifyResultListener(li);
unify.unifyParallel(unifyCons.getUndConstraints(), oderConstraints, finiteClosure, logFile, log, urm,
@@ -730,6 +729,7 @@ public class JavaTXCompiler {
System.out.println("Constraints for Generated Generics: " + " ???");
logFile.write("RES_FINAL: " + li.getResults().toString() + "\n");
logFile.flush();
statistics.close();
return li.getResults();
}
/* UnifyResultModel End */
@@ -738,7 +738,7 @@ public class JavaTXCompiler {
// oderConstraints, finiteClosure, logFile, log, new UnifyResultModel(cons,
// finiteClosure));
Set<Set<UnifyPair>> result = unify.unifyOderConstraints(unifyCons.getUndConstraints(), oderConstraints,
finiteClosure, logFile, log, new UnifyResultModel(cons, finiteClosure), usedTasks);
finiteClosure, logFile, log, new UnifyResultModelParallel(cons, finiteClosure), usedTasks);
System.out.println("RESULT: " + result);
logFile.write("RES: " + result.toString() + "\n");
logFile.flush();
@@ -765,6 +765,7 @@ public class JavaTXCompiler {
} catch (IOException e) {
System.err.println("kein LogFile");
}
statistics.close();
return results.stream()
.map((unifyPairs -> new ResultSet(UnifyTypeFactory.convert(unifyPairs, Pair.generateTPHMap(cons)))))
.collect(Collectors.toList());

View File

@@ -49,17 +49,4 @@ public class GenericDeclarationList extends SyntaxTreeNode implements Iterable<G
public String toString() {
return this.gtvs.toString();
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
GenericDeclarationList that = (GenericDeclarationList) o;
return gtvs.equals(that.gtvs);
}
@Override
public int hashCode() {
return Objects.hash(gtvs);
}
}

View File

@@ -6,7 +6,6 @@ import org.antlr.v4.runtime.Token;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
/**
* Entspricht einem GenericTypeVar, jedoch mit Bounds
@@ -46,7 +45,7 @@ public class GenericTypeVar extends SyntaxTreeNode
public String toString()
{
return "BoGTV " + this.name + " " + this.bounds;
return "BoGTV " + this.name;
}
public String getName(){
@@ -62,17 +61,4 @@ public class GenericTypeVar extends SyntaxTreeNode
public void accept(ASTVisitor visitor) {
visitor.visit(this);
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
GenericTypeVar that = (GenericTypeVar) o;
return bounds.equals(that.bounds) && name.equals(that.name);
}
@Override
public int hashCode() {
return Objects.hash(bounds, name);
}
}

View File

@@ -1,16 +1,19 @@
package de.dhbwstuttgart.syntaxtree.factory;
import java.io.IOException;
import java.lang.reflect.*;
import java.lang.reflect.Constructor;
import java.lang.reflect.Type;
import java.nio.file.Files;
import java.nio.file.Path;
import java.util.*;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashSet;
import java.util.List;
import java.util.Optional;
import java.util.Set;
import de.dhbwstuttgart.bytecode.JavaTXSignatureAttribute;
import de.dhbwstuttgart.exceptions.NotImplementedException;
import de.dhbwstuttgart.parser.NullToken;
import de.dhbwstuttgart.parser.SyntaxTreeGenerator.GenericContext;
import de.dhbwstuttgart.parser.scope.JavaClassName;
import de.dhbwstuttgart.parser.scope.JavaClassRegistry;
import de.dhbwstuttgart.syntaxtree.Field;
import de.dhbwstuttgart.syntaxtree.Method;
import de.dhbwstuttgart.syntaxtree.type.*;
@@ -19,14 +22,7 @@ import de.dhbwstuttgart.syntaxtree.*;
import de.dhbwstuttgart.syntaxtree.statement.Block;
import de.dhbwstuttgart.syntaxtree.statement.Statement;
import de.dhbwstuttgart.syntaxtree.type.WildcardType;
import de.dhbwstuttgart.target.tree.type.TargetRefType;
import de.dhbwstuttgart.util.Pair;
import javassist.bytecode.SignatureAttribute;
import org.antlr.v4.runtime.Token;
import org.apache.commons.io.IOUtils;
import org.objectweb.asm.*;
import org.objectweb.asm.signature.SignatureReader;
import org.objectweb.asm.signature.SignatureVisitor;
/**
* Anmerkung:
@@ -36,76 +32,21 @@ import org.objectweb.asm.signature.SignatureVisitor;
public class ASTFactory {
public static ClassOrInterface createClass(java.lang.Class jreClass){
// TODO Inner classes
var methodSignatures = new HashMap<Pair<String, String>, String>();
String classSignature = null;
// Load class with asm to figure out if there's a JavaTX signature
try {
var path = jreClass.getName().replace('.', '/') + ".class";
var classLoader = jreClass.getClassLoader();
if (classLoader != null) {
var bytes = IOUtils.toByteArray(Objects.requireNonNull(classLoader.getResourceAsStream(path)));
var classReader = new ClassReader(bytes);
var classVisitor = new ClassVisitor(Opcodes.ASM7) {
String classSignature;
@Override
public void visitAttribute(Attribute attribute) {
if (attribute.type.equals("JavaTXSignature")) {
classSignature = ((JavaTXSignatureAttribute) attribute).signature;
}
super.visitAttribute(attribute);
}
@Override
public void visit(int version, int access, String name, String signature, String superName, String[] interfaces) {
classSignature = signature;
super.visit(version, access, name, signature, superName, interfaces);
}
@Override
public MethodVisitor visitMethod(int access, String name, String descriptor, String signature, String[] exceptions) {
methodSignatures.put(new Pair<>(name, descriptor), signature);
return new MethodVisitor(Opcodes.ASM7) {
@Override
public void visitAttribute(Attribute attribute) {
if (attribute.type.equals("JavaTXSignature")) {
methodSignatures.put(new Pair<>(name, descriptor), ((JavaTXSignatureAttribute) attribute).signature);
}
super.visitAttribute(attribute);
}
};
}
};
classReader.accept(classVisitor, new Attribute[]{new JavaTXSignatureAttribute()}, ClassReader.SKIP_CODE | ClassReader.SKIP_DEBUG | ClassReader.SKIP_FRAMES);
classSignature = classVisitor.classSignature;
}
} catch (IOException e) {
// Skip
}
JavaClassName name = new JavaClassName(jreClass.getName());
List<Method> methoden = new ArrayList<>();
List<de.dhbwstuttgart.syntaxtree.Constructor> konstruktoren = new ArrayList<>();
for(java.lang.reflect.Constructor constructor : jreClass.getConstructors()){
var signature = methodSignatures.get(new Pair<>(constructor.getName(), org.objectweb.asm.Type.getConstructorDescriptor(constructor)));
createConstructor(constructor, signature, jreClass).map(c -> konstruktoren.add(c));
for(java.lang.reflect.Constructor constructor : jreClass.getDeclaredConstructors()){
createConstructor(constructor, jreClass).map(c -> konstruktoren.add(c));
}
Set<java.lang.reflect.Method> allMethods = new HashSet<>(Arrays.asList(jreClass.getMethods()));
Set<java.lang.reflect.Method> allDeclaredMethods = new HashSet<>(Arrays.asList(jreClass.getDeclaredMethods()));
Set<java.lang.reflect.Method> allInheritedMethods = new HashSet<>(allMethods);
allInheritedMethods.removeAll(allDeclaredMethods);
for(java.lang.reflect.Method method : allDeclaredMethods){
var signature = methodSignatures.get(new Pair<>(method.getName(), org.objectweb.asm.Type.getMethodDescriptor(method)));
methoden.add(createMethod(method, signature, jreClass, false));
methoden.add(createMethod(method, jreClass, false));
}
for(java.lang.reflect.Method method : allInheritedMethods){
var signature = methodSignatures.get(new Pair<>(method.getName(), org.objectweb.asm.Type.getMethodDescriptor(method)));
methoden.add(createMethod(method, signature, jreClass, true));
methoden.add(createMethod(method, jreClass, true));
}
List<Field> felder = new ArrayList<>();
for(java.lang.reflect.Field field : jreClass.getDeclaredFields()){
@@ -131,8 +72,7 @@ public class ASTFactory {
for(Type jreInterface : jreClass.getGenericInterfaces()){
implementedInterfaces.add((RefType) createType(jreInterface));
}
GenericDeclarationList genericDeclarationList = createGenerics(jreClass.getTypeParameters(), jreClass, null, classSignature);
GenericDeclarationList genericDeclarationList = createGenerics(jreClass.getTypeParameters(), jreClass, null);
Token offset = new NullToken(); //Braucht keinen Offset, da diese Klasse nicht aus einem Quellcode geparst wurde
@@ -147,7 +87,7 @@ public class ASTFactory {
// return createClass(classType).getType();
//}
private static Optional<de.dhbwstuttgart.syntaxtree.Constructor> createConstructor(Constructor constructor, String signature, Class inClass) {
private static Optional<de.dhbwstuttgart.syntaxtree.Constructor> createConstructor(Constructor constructor, Class inClass) {
String name = constructor.getName();
RefTypeOrTPHOrWildcardOrGeneric returnType = createType(inClass);
Parameter[] jreParams = constructor.getParameters();
@@ -161,7 +101,7 @@ public class ASTFactory {
}
ParameterList parameterList = new ParameterList(params, new NullToken());
Block block = new Block(new ArrayList<Statement>(), new NullToken());
GenericDeclarationList gtvDeclarations = createGenerics(constructor.getTypeParameters(), inClass, constructor.getName(), signature);
GenericDeclarationList gtvDeclarations = createGenerics(constructor.getTypeParameters(), inClass, constructor.getName());
Token offset = new NullToken();
int modifier = constructor.getModifiers();
@@ -172,7 +112,7 @@ public class ASTFactory {
return Optional.of(new de.dhbwstuttgart.syntaxtree.Constructor(modifier, name,returnType, parameterList, block, gtvDeclarations, offset /*, new ArrayList<>() geloescht PL 2018-11-24 */));
}
public static Method createMethod(java.lang.reflect.Method jreMethod, String signature, java.lang.Class inClass, Boolean isInherited){
public static Method createMethod(java.lang.reflect.Method jreMethod, java.lang.Class inClass, Boolean isInherited){
String name = jreMethod.getName();
RefTypeOrTPHOrWildcardOrGeneric returnType;
Type jreRetType;
@@ -193,142 +133,19 @@ public class ASTFactory {
}
ParameterList parameterList = new ParameterList(params, new NullToken());
Block block = new Block(new ArrayList<Statement>(), new NullToken());
GenericDeclarationList gtvDeclarations = createGenerics(jreMethod.getTypeParameters(), inClass, jreMethod.getName(), signature);
GenericDeclarationList gtvDeclarations = createGenerics(jreMethod.getTypeParameters(), inClass, jreMethod.getName());
Token offset = new NullToken();
return new Method(jreMethod.getModifiers(), name,returnType, parameterList, block, gtvDeclarations, offset, isInherited);
}
public static GenericDeclarationList createGenerics(TypeVariable[] typeParameters, Class context, String methodName, String signature) {
if (signature == null) {
List<de.dhbwstuttgart.syntaxtree.GenericTypeVar> gtvs = new ArrayList<>();
for(TypeVariable jreTV : typeParameters){
de.dhbwstuttgart.syntaxtree.GenericTypeVar gtv = createGeneric(jreTV, jreTV.getName(), context, methodName);
gtvs.add(gtv);
}
return new GenericDeclarationList(gtvs, new NullToken());
} else {
var res = createGenerics(signature);
return res;
public static GenericDeclarationList createGenerics(TypeVariable[] typeParameters, Class context, String methodName){
List<de.dhbwstuttgart.syntaxtree.GenericTypeVar> gtvs = new ArrayList<>();
for(TypeVariable jreTV : typeParameters){
de.dhbwstuttgart.syntaxtree.GenericTypeVar gtv = createGeneric(jreTV, jreTV.getName(), context, methodName);
gtvs.add(gtv);
}
}
public static GenericDeclarationList createGenerics(String signature) {
if (signature == null) return new GenericDeclarationList(new ArrayList<>(), new NullToken());
var gtvs = new ArrayList<GenericTypeVar>();
var signatureVisitor = new SignatureVisitor(Opcodes.ASM7) {
List<RefTypeOrTPHOrWildcardOrGeneric> bounds = new ArrayList<>();
final Stack<RefTypeOrTPHOrWildcardOrGeneric> bound = new Stack<>();
final Stack<RefType> classTypes = new Stack<>();
// All hail the mighty visitor pattern
final SignatureVisitor doNothing = new SignatureVisitor(Opcodes.ASM7) {};
char wildcard = '=';
@Override
public SignatureVisitor visitSuperclass() {
return doNothing;
}
@Override
public SignatureVisitor visitParameterType() {
return doNothing;
}
@Override
public SignatureVisitor visitReturnType() {
return doNothing;
}
@Override
public SignatureVisitor visitExceptionType() {
return doNothing;
}
@Override
public void visitFormalTypeParameter(String name) {
bounds = new ArrayList<>();
gtvs.add(new GenericTypeVar(name, bounds, new NullToken(), new NullToken()));
}
@Override
public void visitTypeVariable(String name) {
var refType = new GenericRefType(name, new NullToken());
if (classTypes.isEmpty()) {
((List<RefTypeOrTPHOrWildcardOrGeneric>) gtvs.get(gtvs.size() - 1).getBounds()).add(refType);
} else {
pushType(refType);
}
}
@Override
public void visitClassType(String name) {
var refType = new RefType(new JavaClassName(name.replaceAll("/", ".")), new ArrayList<>(), new NullToken());
classTypes.push(refType);
pushType(refType);
}
void pushType(RefTypeOrTPHOrWildcardOrGeneric refType) {
if (wildcard == SignatureVisitor.SUPER) {
bound.push(new SuperWildcardType(refType, new NullToken()));
} else if (wildcard == SignatureVisitor.EXTENDS) {
bound.push(new ExtendsWildcardType(refType, new NullToken()));
} else {
bound.push(refType);
}
}
@Override
public SignatureVisitor visitTypeArgument(char wildcard) {
this.wildcard = wildcard;
return this;
}
boolean equals(RefTypeOrTPHOrWildcardOrGeneric a, RefTypeOrTPHOrWildcardOrGeneric b) {
if (b instanceof SuperWildcardType wc)
return equals(a, wc.getInnerType());
else if (b instanceof ExtendsWildcardType wc)
return equals(a, wc.getInnerType());
return a == b;
}
@Override
public void visitEnd() {
wildcard = '=';
var classType = (RefType) classTypes.pop();
if (!classTypes.isEmpty()) {
var next = classTypes.peek();
var par = bound.pop();
var toAdd = new ArrayList<RefTypeOrTPHOrWildcardOrGeneric>();
while (!equals(next, par)) {
toAdd.add(par);
par = bound.pop();
}
var element = par;
if (par instanceof WildcardType wc) {
element = wc.getInnerType();
}
Collections.reverse(toAdd);
((RefType) element).getParaList().addAll(toAdd);
bound.push(par);
} else {
if (bound.peek() != classType) {
classType.getParaList().add(bound.pop());
bounds.add(classType);
} else {
bounds.add(bound.pop());
}
}
}
};
var sr = new SignatureReader(signature);
sr.accept(signatureVisitor);
return new GenericDeclarationList(gtvs, new NullToken());
return new GenericDeclarationList(gtvs,new NullToken());
}
private static RefTypeOrTPHOrWildcardOrGeneric createType(java.lang.reflect.Type type){

View File

@@ -5,8 +5,6 @@ import de.dhbwstuttgart.syntaxtree.ASTVisitor;
import de.dhbwstuttgart.typeinference.result.ResultSetVisitor;
import org.antlr.v4.runtime.Token;
import java.util.Objects;
/**
* Stellt eine Wildcard mit oberer Grenze dar.
* z.B. void test(? extends Number var){..}
@@ -56,16 +54,9 @@ public class ExtendsWildcardType extends WildcardType{
visitor.visit(this);
}
@Override
public int hashCode() {
return Objects.hashCode(this.innerType);
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
ExtendsWildcardType that = (ExtendsWildcardType) o;
return that.innerType.equals(this.innerType);
// TODO Auto-generated method stub
return false;
}
}

View File

@@ -4,8 +4,6 @@ import de.dhbwstuttgart.syntaxtree.ASTVisitor;
import de.dhbwstuttgart.typeinference.result.ResultSetVisitor;
import org.antlr.v4.runtime.Token;
import java.util.Objects;
public class GenericRefType extends RefTypeOrTPHOrWildcardOrGeneric
{
private String name;
@@ -35,20 +33,14 @@ public class GenericRefType extends RefTypeOrTPHOrWildcardOrGeneric
visitor.visit(this);
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
GenericRefType that = (GenericRefType) o;
return name.equals(that.name);
}
@Override
public int hashCode() {
return Objects.hash(name);
}
@Override
@Override
public boolean equals(Object o) {
// TODO Auto-generated method stub
return false;
}
@Override
public String toString()
{
return "GTV " + this.name;

View File

@@ -2,12 +2,9 @@ package de.dhbwstuttgart.syntaxtree.type;
import de.dhbwstuttgart.syntaxtree.ASTVisitor;
import de.dhbwstuttgart.syntaxtree.GenericTypeVar;
import de.dhbwstuttgart.typeinference.result.ResultSetVisitor;
import org.antlr.v4.runtime.Token;
import java.util.Objects;
/**
* Stellt eine Wildcard mit unterer Grenze dar.
* z.B. void test(? super Integer var){..}
@@ -68,16 +65,9 @@ public class SuperWildcardType extends WildcardType{
visitor.visit(this);
}
@Override
public int hashCode() {
return Objects.hashCode(this.innerType);
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
SuperWildcardType that = (SuperWildcardType) o;
return that.innerType.equals(this.innerType);
// TODO Auto-generated method stub
return false;
}
}

View File

@@ -16,10 +16,8 @@ import de.dhbwstuttgart.target.tree.expression.TargetExpression;
import de.dhbwstuttgart.target.tree.type.*;
import de.dhbwstuttgart.typeinference.constraints.Pair;
import de.dhbwstuttgart.typeinference.result.*;
import org.objectweb.asm.Attribute;
import java.util.*;
import java.util.concurrent.CyclicBarrier;
import java.util.stream.Collectors;
import java.util.stream.Stream;
@@ -172,6 +170,7 @@ public class ASTToTargetAST {
for (var pair : simplifiedConstraints) {
if (pair.left.equals(typeVariable) && typeVariables.contains(pair.right)) {
addToPairs(result, new PairTPHsmallerTPH(pair.left, equality.getOrDefault(pair.right, pair.right)));
typeVariables.add(pair.right);
}
}
}
@@ -197,7 +196,7 @@ public class ASTToTargetAST {
RefTypeOrTPHOrWildcardOrGeneric T2 = superType;
if (T2 instanceof TypePlaceholder tph) T2 = equality.getOrDefault(tph, tph);
System.out.println("T1s: " + T1s + " T2: " + T2);
System.out.println("T1s: " + T1s + "\nT2: " + T2);
//Ende
superType = methodCall.receiverType;
@@ -212,7 +211,7 @@ public class ASTToTargetAST {
var optMethod = findMethod(owner, methodCall.name, methodCall.getArgumentList());
if (optMethod.isEmpty()) return;
var method = optMethod.get();
var generics = generics(owner, method).txGenerics();
var generics = generics(owner, method).javaGenerics();
// transitive and
var all = transitiveClosure(generics);
@@ -227,24 +226,24 @@ public class ASTToTargetAST {
// Loop from hell
outer:
for (var R1 : typeVariables) {
if (typeVariablesOfClass.contains(R1)) continue;
for (var tph : typeVariables) {
if (typeVariablesOfClass.contains(tph)) continue;
for (var generic : all) {
if (!(generic.getRight() instanceof TypePlaceholder type))
continue;
for (var pair : simplifiedConstraints) {
if (!(pair.left.equals(R1) && pair.right.equals(generic.getLeft())))
if (!(pair.left.equals(tph) && pair.right.equals(generic.getLeft())))
continue;
for (var R2 : typeVariables) {
for (var tph2 : typeVariables) {
for (var pair2 : simplifiedConstraints) {
if (!(pair2.right.equals(R2) && pair2.left.equals(type)))
if (!(pair2.right.equals(tph2) && pair2.left.equals(type)))
continue;
if (R1.equals(R2)) continue;
if (!T1s.contains(R1) || !R2.equals(T2)) continue;
if (tph.equals(tph2)) continue;
if (!T1s.contains(tph) || !tph2.equals(T2)) continue;
var newPair = new PairTPHsmallerTPH(R1, R2);
var newPair = new PairTPHsmallerTPH(tph, tph2);
newPairs.add(newPair);
if (!containsRelation(result, newPair))
@@ -269,7 +268,7 @@ public class ASTToTargetAST {
@Override
public void visit(Assign assign) {
superType = assign.rightSide.getType();
superType = assign.lefSide.getType();
assign.rightSide.accept(this);
}
@@ -522,6 +521,9 @@ public class ASTToTargetAST {
super.visit(methodCall);
typeVariables.addAll(findTypeVariables(methodCall.getType(), equality));
}
@Override
public void visit(Assign assign) {}
});
}
@@ -552,11 +554,10 @@ public class ASTToTargetAST {
methodFindConstraints(owner, method, simplifiedConstraints, txTypeVariables, classGenerics.userDefinedGenerics, txTypeVariablesOfClass, txResult, txEquality);
{ // Java Generics
eliminateTransitives(javaResult);
var referenced = new HashSet<TypePlaceholder>();
eliminateCycles(javaResult, equality, referenced);
eliminateInfima(javaResult, equality);
eliminateInfima(javaResult, equality, referenced);
var usedTphs = new HashSet<TypePlaceholder>();
// For eliminating inner type variables we need to figure out which ones are actually used
@@ -570,13 +571,11 @@ public class ASTToTargetAST {
eliminateInnerTypeVariables(referenced, javaResult);
equalizeTypeVariables(javaResult, equality);
usedTPHsOfMethods.put(method, usedTphs);
addMissingObjectBounds(javaResult, genericsOfClass);
}
{
var referenced = new HashSet<TypePlaceholder>();
// JavaTX Generics
eliminateTransitives(txResult);
eliminateInfima(txResult, txEquality);
eliminateInfima(txResult, txEquality, referenced);
for (var param : method.getParameterList().getFormalparalist()) {
referenced.addAll(findTypeVariables(param.getType(), txEquality));
@@ -585,36 +584,12 @@ public class ASTToTargetAST {
referenced.addAll(txTypeVariablesOfClass);
eliminateInnerTypeVariables(referenced, txResult);
addMissingObjectBounds(txResult, txGenericsOfClass);
}
System.out.println(method.name + ": " + txResult + " & " + javaResult);
return generics;
}
private void eliminateChain(Set<ResultPair<?, ?>> result, List<TypePlaceholder> chain) {
for (var pair : new HashSet<>(result)) {
if (pair instanceof PairTPHsmallerTPH ptph && chain.get(chain.size() - 1).equals(ptph.left)) {
if (chain.contains(ptph.right)) return;
var copy = new ArrayList<>(chain);
copy.add(ptph.right);
if (copy.size() > 2)
result.remove(new PairTPHsmallerTPH(chain.get(0), ptph.right));
eliminateChain(result, copy);
}
}
}
void eliminateTransitives(Set<ResultPair<?,?>> result) {
for (var pair : new HashSet<>(result)) if (pair instanceof PairTPHsmallerTPH ptph) {
var first = ptph.left;
var chain = new ArrayList<TypePlaceholder>();
chain.add(ptph.left);
chain.add(ptph.right);
eliminateChain(result, chain);
}
}
void findAllBounds(RefTypeOrTPHOrWildcardOrGeneric type, Set<ResultPair<?, ?>> generics, Map<TypePlaceholder, TypePlaceholder> equality) {
if (type instanceof TypePlaceholder tph) {
tph = equality.getOrDefault(tph, tph);
@@ -659,86 +634,34 @@ public class ASTToTargetAST {
findAllBounds(field.getType(), txResult, txEquality);
}
eliminateTransitives(javaResult);
eliminateTransitives(txResult);
System.out.println(javaResult);
var referenced = new HashSet<TypePlaceholder>();
eliminateCycles(javaResult, equality, referenced);
eliminateInfima(javaResult, equality);
eliminateInfima(javaResult, equality, referenced);
var txReferenced = new HashSet<TypePlaceholder>();
eliminateInfima(txResult, txEquality);
eliminateInfima(txResult, txEquality, txReferenced);
eliminateInnerTypeVariablesOfClass(classOrInterface, javaResult, equality, referenced);
equalizeTypeVariables(javaResult, equality);
eliminateInnerTypeVariablesOfClass(classOrInterface, txResult, txEquality, txReferenced);
addMissingObjectBounds(javaResult, null);
addMissingObjectBounds(txResult, null);
System.out.println("Class " + classOrInterface.getClassName().getClassName() + ": " + txResult + ", " + javaResult);
return generics;
}
void addMissingObjectBounds(Set<ResultPair<?,?>> result, Set<ResultPair<?, ?>> filter) {
outer: for (var p1 : new HashSet<>(result)) {
if (p1 instanceof PairTPHsmallerTPH ptph) {
for (var p2 : new HashSet<>(result)) {
if (ptph.right.equals(p2.getLeft()))
continue outer;
}
if (filter == null || filter.stream().noneMatch((pair) -> pair.getLeft().equals(ptph.right)))
result.add(new PairTPHequalRefTypeOrWildcardType(ptph.right, OBJECT));
}
}
}
void equalizeTypeVariables(Set<ResultPair<?, ?>> input, Map<TypePlaceholder, TypePlaceholder> equality) {
System.out.println(input);
for (var pair : new HashSet<>(input)) {
if (pair instanceof PairTPHsmallerTPH ptph) {
var chain = new ArrayList<TypePlaceholder>();
chain.add(ptph.left);
chain.add(ptph.right);
outer: while (true) {
var added = false;
for (var pair2 : input) {
if (pair2 instanceof PairTPHsmallerTPH ptph2 && ptph2.left.equals(chain.get(chain.size() - 1))) {
if (chain.contains(ptph2.right)) break outer;
chain.add(ptph2.right);
added = true;
System.out.println(pair + " " + ptph.left.getVariance() + " " + ptph.right.getVariance());
if (ptph.left.getVariance() == 1 && ptph.right.getVariance() == -1) {
addToEquality(equality, ptph.left, ptph.right);
input.remove(ptph);
for (var pair2 : new HashSet<>(simplifiedConstraints)) {
if (pair2.right.equals(ptph.left)) {
simplifiedConstraints.remove(pair2);
simplifiedConstraints.add(new PairTPHsmallerTPH(pair2.left, ptph.right));
}
}
if (!added) break;
}
var variance = chain.get(0).getVariance();
if (variance != 1) continue;
var index = 0;
for (var tph : chain) {
if (variance == 1 && tph.getVariance() == -1) {
variance = -1;
}
if (variance == -1 && tph.getVariance() == 1) {
break;
}
index++;
}
if (variance == 1) continue;
var start = chain.get(0);
var prev = start;
for (var i = 1; i < index; i++) {
var cur = chain.get(i);
addToEquality(equality, cur, start);
input.remove(new PairTPHsmallerTPH(prev, chain.get(i)));
for (var pair2 : new HashSet<>(input)) {
// TODO Maybe this would be unnecessary if we were to add the = constraints later on
if (pair2 instanceof PairTPHequalRefTypeOrWildcardType && pair2.getLeft().equals(cur)) {
input.remove(pair2);
input.add(new PairTPHequalRefTypeOrWildcardType(start, pair2.getRight()));
}
}
prev = chain.get(i);
}
}
}
@@ -816,15 +739,6 @@ public class ASTToTargetAST {
var cycles = findCycles(input);
for (var cycle : cycles) {
var newTph = TypePlaceholder.fresh(new NullToken());
var variance = cycle.get(0).getVariance();
for (var tph : cycle) {
if (tph.getVariance() != variance) {
variance = 0;
break;
}
}
newTph.setVariance(variance);
referenced.add(newTph);
addToPairs(input, new PairTPHequalRefTypeOrWildcardType(newTph, OBJECT));
cycle.add(cycle.get(0)); // Make it a complete cycle
@@ -838,7 +752,7 @@ public class ASTToTargetAST {
}
}
void eliminateInfima(Set<ResultPair<?, ?>> input, Map<TypePlaceholder, TypePlaceholder> equality) {
void eliminateInfima(Set<ResultPair<?, ?>> input, Map<TypePlaceholder, TypePlaceholder> equality, Set<TypePlaceholder> referenced) {
var foundInfima = false;
do {
foundInfima = false;
@@ -853,16 +767,7 @@ public class ASTToTargetAST {
if (infima.size() > 1) {
foundInfima = true;
var newTph = TypePlaceholder.fresh(new NullToken());
var variance = infima.stream().findFirst().get().right.getVariance();
for (var pair : infima) {
if (pair.right.getVariance() != variance) {
variance = 0;
break;
}
}
newTph.setVariance(variance);
//referenced.add(newTph);
referenced.add(newTph);
addToPairs(input, new PairTPHsmallerTPH(left, newTph));
input.removeAll(infima);
for (var infimum : infima) {

View File

@@ -22,15 +22,11 @@ public record TargetMethod(int access, String name, TargetBlock block, Signature
}
public static String getSignature(Set<TargetGeneric> generics, List<MethodParameter> parameters, TargetType returnType) {
String ret = "";
if (generics.size() > 0) {
ret += "<";
for (var generic : generics) {
ret += generic.name() + ":" + generic.bound().toDescriptor();
}
ret += ">";
String ret = "<";
for (var generic : generics) {
ret += generic.name() + ":" + generic.bound().toDescriptor();
}
ret += "(";
ret += ">(";
for (var param : parameters) {
ret += param.type().toDescriptor();
}

View File

@@ -495,7 +495,7 @@ public class TYPEStmt implements StatementVisitor{
@Override
public void visit(Return returnExpr) {
returnExpr.retexpr.accept(this);
constraintsSet.addUndConstraint(new Pair(returnExpr.getType(),info.getCurrentTypeScope().getReturnType(), PairOperator.SMALLERDOT));
constraintsSet.addUndConstraint(new Pair(returnExpr.getType(),info.getCurrentTypeScope().getReturnType(), PairOperator.EQUALSDOT));
}
@Override
@@ -610,8 +610,8 @@ public class TYPEStmt implements StatementVisitor{
//Fuer Bytecodegenerierung PL 2020-03-09 wird derzeit nicht benutzt ENDE
methodConstraint.add(new Pair(assumption.getReturnType(resolver), forMethod.getType(), PairOperator.SMALLERDOT));
extendsMethodConstraint.add(new Pair(assumption.getReturnType(resolver), forMethod.getType(), PairOperator.SMALLERDOT));
methodConstraint.add(new Pair(assumption.getReturnType(resolver), forMethod.getType(), PairOperator.EQUALSDOT));
extendsMethodConstraint.add(new Pair(assumption.getReturnType(resolver), forMethod.getType(), PairOperator.EQUALSDOT));
//methodConstraint.add(new Pair(assumption.getReturnType(resolver), forMethod.getType(), PairOperator.EQUALSDOT));
//extendsMethodConstraint.add(new Pair(assumption.getReturnType(resolver), forMethod.getType(), PairOperator.EQUALSDOT));

View File

@@ -9,10 +9,12 @@ import java.util.Optional;
import java.util.Queue;
import java.util.Set;
import java.util.Stack;
import java.util.concurrent.ForkJoinPool;
import java.util.function.Function;
import java.util.stream.Collectors;
import de.dhbwstuttgart.exceptions.DebugException;
import de.dhbwstuttgart.syntaxtree.type.ExtendsWildcardType;
import de.dhbwstuttgart.typeinference.unify.interfaces.IFiniteClosure;
import de.dhbwstuttgart.typeinference.unify.interfaces.IRuleSet;
import de.dhbwstuttgart.typeinference.unify.model.ExtendsType;
@@ -43,14 +45,14 @@ import org.apache.commons.io.output.NullOutputStream;
*/
public class RuleSet implements IRuleSet{
Writer logFile;
WriterActiveObject logFile;
public RuleSet() {
super();
logFile = new OutputStreamWriter(new NullOutputStream());
logFile = new WriterActiveObject(new OutputStreamWriter(new NullOutputStream()), ForkJoinPool.commonPool());
}
RuleSet(Writer logFile) {
RuleSet(WriterActiveObject logFile) {
this.logFile = logFile;
}
@@ -390,26 +392,51 @@ public class RuleSet implements IRuleSet{
if((pair.getPairOp() != PairOperator.SMALLERDOT) && (pair.getPairOp() != PairOperator.SMALLERNEQDOT))
return false;
if (pair.getPairOp() == PairOperator.SMALLERNEQDOT) {
UnifyType lhs = pair.getLhsType();
UnifyType rhs = pair.getRhsType();
if (lhs instanceof WildcardType) {
lhs = ((WildcardType)lhs).getWildcardedType();
}
if (rhs instanceof WildcardType) {
rhs = ((WildcardType)rhs).getWildcardedType();
}
if (lhs.equals(rhs)){
return false;
}
UnifyType lhsType = pair.getLhsType();
UnifyType rhsType = pair.getRhsType();
/*
* ty <. ? extends ty' is wrong
*/
if (rhsType instanceof ExtendsType) {
return false;
}
/*
* ? super ty <. ty' is wrong
* except Ty' = Object or ty' = ? super Object
*/
if ((lhsType instanceof SuperType) &&
(!(rhsType.equals(new ReferenceType("java.lang.Object", false)))) &&
!(rhsType.equals(new SuperType (new ReferenceType("java.lang.Object", false))))) {
return false;
}
/*
* ? extends ty <. ty' is equivalent to ty < ty'
*/
if (lhsType instanceof ExtendsType) {
lhsType = ((WildcardType)lhsType).getWildcardedType();
}
/*
* ty <. ? super ty' ist equivalent to ty <. ty'
*/
if (rhsType instanceof SuperType) {
rhsType = ((WildcardType)rhsType).getWildcardedType();
}
/*
* SMALLERNEQDOT => type must not be equal
*/
if (pair.getPairOp() == PairOperator.SMALLERNEQDOT && lhsType.equals(rhsType)){
return false;
}
UnifyType lhsType = pair.getLhsType();
if(!(lhsType instanceof ReferenceType) && !(lhsType instanceof PlaceholderType))
return false;
UnifyType rhsType = pair.getRhsType();
if(!(rhsType instanceof ReferenceType) && !(rhsType instanceof PlaceholderType))
return false;
@@ -841,14 +868,8 @@ public class RuleSet implements IRuleSet{
UnifyType r = x.getRhsType();
if (r instanceof PlaceholderType) { ((PlaceholderType)r).disableWildcardtable(); }
} );
try {
logFile.write("FUNgreater: " + pair + "\n");
logFile.write("FUNred: " + result + "\n");
logFile.flush();
}
catch (IOException e) {
System.out.println("logFile-Error");
}
logFile.write("FUNgreater: " + pair + "\n");
logFile.write("FUNred: " + result + "\n");
return Optional.of(result);
}
@@ -891,14 +912,10 @@ public class RuleSet implements IRuleSet{
UnifyType r = x.getRhsType();
if (r instanceof PlaceholderType) { ((PlaceholderType)r).disableWildcardtable(); }
} );
try {
logFile.write("FUNgreater: " + pair + "\n");
logFile.write("FUNgreater: " + result + "\n");
logFile.flush();
}
catch (IOException e) {
System.out.println("lofFile-Error");
}
logFile.write("FUNgreater: " + pair + "\n");
logFile.write("FUNgreater: " + result + "\n");
return Optional.of(result);
}
@@ -941,14 +958,9 @@ public class RuleSet implements IRuleSet{
UnifyType r = x.getRhsType();
if (r instanceof PlaceholderType) { ((PlaceholderType)r).disableWildcardtable(); }
} );
try {
logFile.write("FUNgreater: " + pair + "\n");
logFile.write("FUNsmaller: " + result + "\n");
logFile.flush();
}
catch (IOException e) {
System.out.println("lofFile-Error");
}
logFile.write("FUNgreater: " + pair + "\n");
logFile.write("FUNsmaller: " + result + "\n");
return Optional.of(result);
}

View File

@@ -1,23 +1,17 @@
package de.dhbwstuttgart.typeinference.unify;
import java.io.FileWriter;
import java.io.IOException;
import java.io.Writer;
import java.util.ArrayList;
import java.util.List;
import java.util.Set;
import java.util.concurrent.ForkJoinPool;
import de.dhbwstuttgart.core.JavaTXCompiler;
import de.dhbwstuttgart.typeinference.constraints.Constraint;
import de.dhbwstuttgart.typeinference.constraints.ConstraintSet;
import de.dhbwstuttgart.typeinference.constraints.Pair;
import de.dhbwstuttgart.typeinference.unify.interfaces.IFiniteClosure;
import de.dhbwstuttgart.typeinference.unify.model.FiniteClosure;
import de.dhbwstuttgart.typeinference.unify.model.UnifyPair;
public class TypeUnify {
public static Writer statistics;
/**
* unify parallel ohne result modell
* @param undConstrains
@@ -25,21 +19,15 @@ public class TypeUnify {
* @param fc
* @param logFile
* @param log
* @param cons
* @return
*/
public Set<Set<UnifyPair>> unify(Set<UnifyPair> undConstrains, List<Set<Constraint<UnifyPair>>> oderConstraints, IFiniteClosure fc, Writer logFile, Boolean log, UnifyResultModel ret, UnifyTaskModel usedTasks) {
TypeUnifyTask unifyTask = new TypeUnifyTask(undConstrains, oderConstraints, fc, true, logFile, log, 0, ret, usedTasks);
ForkJoinPool pool = new ForkJoinPool();
public Set<Set<UnifyPair>> unify(Set<UnifyPair> undConstrains, List<Set<Constraint<UnifyPair>>> oderConstraints, IFiniteClosure fc, Writer logFile, Boolean log, UnifyResultModelParallel resultModel, UnifyTaskModelParallel taskModel) {
ForkJoinPool pool = new ForkJoinPool(Runtime.getRuntime().availableProcessors(), ForkJoinPool.defaultForkJoinWorkerThreadFactory, null, true);
taskModel.setPool(pool);
resultModel.setPool(pool);
TypeUnifyTask unifyTask = new TypeUnifyTask(undConstrains, oderConstraints, fc, true, new WriterActiveObject(logFile, pool), log, resultModel, pool);
pool.invoke(unifyTask);
Set<Set<UnifyPair>> res = unifyTask.join();
try {
logFile.write("\nnoShortendElements: " + unifyTask.noShortendElements + "\n");
logFile.flush();
}
catch (IOException e) {
System.err.println("no log-File");
}
return res;
}
@@ -50,15 +38,15 @@ public class TypeUnify {
* @param fc
* @param logFile
* @param log
* @param cons
* @param ret
* @return
*/
public UnifyResultModel unifyAsync(Set<UnifyPair> undConstrains, List<Set<Constraint<UnifyPair>>> oderConstraints, IFiniteClosure fc, Writer logFile, Boolean log, UnifyResultModel ret, UnifyTaskModel usedTasks) {
TypeUnifyTask unifyTask = new TypeUnifyTask(undConstrains, oderConstraints, fc, true, logFile, log, 0, ret, usedTasks);
ForkJoinPool pool = new ForkJoinPool();
public UnifyResultModelParallel unifyAsync(Set<UnifyPair> undConstrains, List<Set<Constraint<UnifyPair>>> oderConstraints, IFiniteClosure fc, Writer logFile, Boolean log, UnifyResultModelParallel resultModel, UnifyTaskModelParallel taskModel) {
ForkJoinPool pool = new ForkJoinPool(Runtime.getRuntime().availableProcessors(), ForkJoinPool.defaultForkJoinWorkerThreadFactory, null, true);
taskModel.setPool(pool);
resultModel.setPool(pool);
TypeUnifyTask unifyTask = new TypeUnifyTask(undConstrains, oderConstraints, fc, true, new WriterActiveObject(logFile, pool), log, resultModel, pool);
pool.invoke(unifyTask);
return ret;
return resultModel;
}
/**
@@ -68,23 +56,19 @@ public class TypeUnify {
* @param fc
* @param logFile
* @param log
* @param cons
* @param ret
* @return
*/
public UnifyResultModel unifyParallel(Set<UnifyPair> undConstrains, List<Set<Constraint<UnifyPair>>> oderConstraints, IFiniteClosure fc, Writer logFile, Boolean log, UnifyResultModel ret, UnifyTaskModel usedTasks) {
TypeUnifyTask unifyTask = new TypeUnifyTask(undConstrains, oderConstraints, fc, true, logFile, log, 0, ret, usedTasks);
ForkJoinPool pool = new ForkJoinPool();
public UnifyResultModelParallel unifyParallel(Set<UnifyPair> undConstrains, List<Set<Constraint<UnifyPair>>> oderConstraints, IFiniteClosure fc, Writer logFile, Boolean log, UnifyResultModelParallel resultModel, UnifyTaskModelParallel taskModel) {
ForkJoinPool pool = new ForkJoinPool(Runtime.getRuntime().availableProcessors(), ForkJoinPool.defaultForkJoinWorkerThreadFactory, null, true);
taskModel.setPool(pool);
resultModel.setPool(pool);
TypeUnifyTask unifyTask = //new TypeUnifyTask(undConstrains, oderConstraints, fc, true, logFile, log, 0, ret, usedTasks);
new TypeUnifyTask(undConstrains, oderConstraints, fc, true, new WriterActiveObject(logFile, pool), log, resultModel, pool, statistics);
pool.invoke(unifyTask);
Set<Set<UnifyPair>> res = unifyTask.join();
try {
logFile.write("\nnoShortendElements: " + unifyTask.noShortendElements +"\n");
logFile.flush();
}
catch (IOException e) {
System.err.println("no log-File");
}
return ret;
unifyTask.join();
return resultModel;
}
/*
@@ -102,19 +86,13 @@ public class TypeUnify {
* @param fc
* @param logFile
* @param log
* @param cons
* @return
*/
public Set<Set<UnifyPair>> unifyOderConstraints(Set<UnifyPair> undConstrains, List<Set<Constraint<UnifyPair>>> oderConstraints, IFiniteClosure fc, Writer logFile, Boolean log, UnifyResultModel ret, UnifyTaskModel usedTasks) {
TypeUnifyTask unifyTask = new TypeUnifyTask(undConstrains, oderConstraints, fc, false, logFile, log, 0, ret, usedTasks);
public Set<Set<UnifyPair>> unifyOderConstraints(Set<UnifyPair> undConstrains, List<Set<Constraint<UnifyPair>>> oderConstraints, IFiniteClosure fc, Writer logFile, Boolean log, UnifyResultModelParallel resultModel, UnifyTaskModelParallel taskModel) {
resultModel.setPool(ForkJoinPool.commonPool());
TypeUnifyTask unifyTask = new TypeUnifyTask(undConstrains, oderConstraints, fc, false, new WriterActiveObject(logFile, ForkJoinPool.commonPool()), log, resultModel, ForkJoinPool.commonPool());
unifyTask.statisticsFile = statistics;
Set<Set<UnifyPair>> res = unifyTask.compute();
try {
logFile.write("\nnoShortendElements: " + unifyTask.noShortendElements +"\n");
logFile.flush();
}
catch (IOException e) {
System.err.println("no log-File");
}
return res;
}

View File

@@ -1,16 +1,11 @@
package de.dhbwstuttgart.typeinference.unify;
import java.io.FileWriter;
import java.io.IOException;
import java.io.Writer;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.concurrent.ForkJoinPool;
import de.dhbwstuttgart.typeinference.constraints.Constraint;
import de.dhbwstuttgart.typeinference.constraints.ConstraintSet;
import de.dhbwstuttgart.typeinference.constraints.Pair;
import de.dhbwstuttgart.typeinference.unify.interfaces.IFiniteClosure;
import de.dhbwstuttgart.typeinference.unify.model.UnifyPair;
@@ -19,8 +14,18 @@ public class TypeUnify2Task extends TypeUnifyTask {
Set<Set<UnifyPair>> setToFlatten;
Set<UnifyPair> methodSignatureConstraintUebergabe;
public TypeUnify2Task(Set<Set<UnifyPair>> setToFlatten, Set<UnifyPair> eq, List<Set<Constraint<UnifyPair>>> oderConstraints, Set<UnifyPair> nextSetElement, IFiniteClosure fc, boolean parallel, Writer logFile, Boolean log, int rekTiefe, UnifyResultModel urm, UnifyTaskModel usedTasks, Set<UnifyPair> methodSignatureConstraintUebergabe) {
super(eq, oderConstraints, fc, parallel, logFile, log, rekTiefe, urm, usedTasks);
//statistics
TypeUnify2Task(Set<Set<UnifyPair>> setToFlatten, Set<UnifyPair> eq,
List<Set<Constraint<UnifyPair>>> oderConstraints,
Set<UnifyPair> nextSetElement,
IFiniteClosure fc, boolean parallel, WriterActiveObject logFile, Boolean log, UnifyResultModelParallel urm,
Set<UnifyPair> methodSignatureConstraintUebergabe, ForkJoinPool pool, Writer statistics) {
this(setToFlatten, eq, oderConstraints, nextSetElement, fc, parallel, logFile, log, urm, methodSignatureConstraintUebergabe, pool );
}
public TypeUnify2Task(Set<Set<UnifyPair>> setToFlatten, Set<UnifyPair> eq, List<Set<Constraint<UnifyPair>>> oderConstraints, Set<UnifyPair> nextSetElement, IFiniteClosure fc, boolean parallel, WriterActiveObject logFile, Boolean log, UnifyResultModelParallel urm, Set<UnifyPair> methodSignatureConstraintUebergabe, ForkJoinPool pool) {
super(eq, oderConstraints, fc, parallel, logFile, log, urm, pool);
this.setToFlatten = setToFlatten;
this.nextSetElement = nextSetElement;
this.methodSignatureConstraintUebergabe = methodSignatureConstraintUebergabe;
@@ -32,35 +37,21 @@ public class TypeUnify2Task extends TypeUnifyTask {
@Override
protected Set<Set<UnifyPair>> compute() {
if (one) {
System.out.println("two");
}
one = true;
Set<Set<UnifyPair>> res = unify2(setToFlatten, eq, oderConstraintsField, fc, parallel, rekTiefeField, methodSignatureConstraintUebergabe);
Set<Set<UnifyPair>> res = unify2(setToFlatten, eq, oderConstraintsField, fc, parallel, methodSignatureConstraintUebergabe);
/*if (isUndefinedPairSetSet(res)) {
return new HashSet<>(); }
else
*/
//writeLog("xxx");
//noOfThread--;
synchronized (usedTasks) {
if (this.myIsCancelled()) {
return new HashSet<>();
}
else {
return res;
}
}
return res;
}
public void closeLogFile() {
try {
logFile.close();
}
catch (IOException ioE) {
System.err.println("no log-File" + thNo);
}
if(parallel){
logFile.close();
}else{
logFile.closeNonThreaded();
}
}
}

View File

@@ -0,0 +1,57 @@
package de.dhbwstuttgart.typeinference.unify;
import de.dhbwstuttgart.syntaxtree.factory.UnifyTypeFactory;
import de.dhbwstuttgart.typeinference.constraints.ConstraintSet;
import de.dhbwstuttgart.typeinference.constraints.Pair;
import de.dhbwstuttgart.typeinference.result.ResultSet;
import de.dhbwstuttgart.typeinference.unify.interfaces.IFiniteClosure;
import de.dhbwstuttgart.typeinference.unify.model.PairOperator;
import de.dhbwstuttgart.typeinference.unify.model.UnifyPair;
import java.util.*;
import java.util.concurrent.ForkJoinPool;
import java.util.stream.Collectors;
public class UnifyResultModelParallel {
private ForkJoinPool pool;
private ConstraintSet<Pair> cons;
private IFiniteClosure fc;
private List<UnifyResultListener> listeners = new ArrayList<>();
public UnifyResultModelParallel(ConstraintSet<Pair> cons, IFiniteClosure fc){
this.cons = cons;
this.fc = fc;
}
public void setPool(ForkJoinPool pool){
this.pool = pool;
}
public void addUnifyResultListener(UnifyResultListener listenerToAdd) {
listeners.add(listenerToAdd);
}
public void removeUnifyResultListener(UnifyResultListener listenerToRemove) {
listeners.remove(listenerToRemove);
}
public void notify(Set<Set<UnifyPair>> eqPrimePrimeSet){
pool.execute(()->{
Set<Set<UnifyPair>> eqPrimePrimeSetRet = eqPrimePrimeSet.stream().map(x -> {
Optional<Set<UnifyPair>> res = new RuleSet().subst(x.stream().map(y -> {
if (y.getPairOp() == PairOperator.SMALLERDOTWC) y.setPairOp(PairOperator.EQUALSDOT);
return y; //alle Paare a <.? b erden durch a =. b ersetzt
}).collect(Collectors.toCollection(HashSet::new)));
if (res.isPresent()) {//wenn subst ein Erg liefert wurde was veraendert
return new TypeUnifyTask().applyTypeUnificationRules(res.get(), fc);
}
else return x; //wenn nichts veraendert wurde wird x zurueckgegeben
}).collect(Collectors.toCollection(HashSet::new));
List<ResultSet> newResult = eqPrimePrimeSetRet.stream().map(unifyPairs ->
new ResultSet(UnifyTypeFactory.convert(unifyPairs, de.dhbwstuttgart.typeinference.constraints.Pair.generateTPHMap(cons))))
.collect(Collectors.toList());
UnifyResultEvent evt = new UnifyResultEvent(newResult);
for (UnifyResultListener listener : listeners) {
listener.onNewTypeResultFound(evt);
}
});
}
}

View File

@@ -1,18 +0,0 @@
package de.dhbwstuttgart.typeinference.unify;
import java.util.ArrayList;
public class UnifyTaskModel {
ArrayList<TypeUnifyTask> usedTasks = new ArrayList<>();
public synchronized void add(TypeUnifyTask t) {
usedTasks.add(t);
}
public synchronized void cancel() {
for(TypeUnifyTask t : usedTasks) {
t.myCancel(true);
}
}
}

View File

@@ -0,0 +1,17 @@
package de.dhbwstuttgart.typeinference.unify;
import java.util.concurrent.ForkJoinPool;
public class UnifyTaskModelParallel {
private ForkJoinPool pool;
public void setPool(ForkJoinPool pool){
this.pool = pool;
}
public void cancel(){
if(this.pool != null) {
this.pool.shutdown();
}
}
}

View File

@@ -0,0 +1,53 @@
package de.dhbwstuttgart.typeinference.unify;
import java.io.IOException;
import java.io.Writer;
import java.util.concurrent.ForkJoinPool;
public class WriterActiveObject {
private Writer writer;
private ForkJoinPool pool;
public WriterActiveObject(Writer writer, ForkJoinPool pool){
this.writer = writer;
this.pool = pool;
}
public void close(){
pool.execute(()->{
try {
writer.close();
} catch (IOException e) {
System.out.println(e.getMessage());
}
});
}
public void write(String message){
pool.execute(()->{
try {
writer.write(message);
writer.flush();
} catch (IOException e) {
throw new RuntimeException(e);
}
});
}
public void writeNonThreaded(String message){
try {
writer.write(message);
writer.flush();
} catch (IOException e) {
throw new RuntimeException(e);
}
}
public void closeNonThreaded(){
try {
writer.close();
} catch (IOException e) {
throw new RuntimeException(e);
}
}
}

View File

@@ -1,6 +1,5 @@
package de.dhbwstuttgart.util;
import java.util.Objects;
import java.util.Optional;
public class Pair<T, T1> {
@@ -23,17 +22,4 @@ public class Pair<T, T1> {
public String toString() {
return "(" + key.toString() + "," + value.toString() + ")\n";
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
Pair<?, ?> pair = (Pair<?, ?>) o;
return Objects.equals(key, pair.key) && Objects.equals(value, pair.value);
}
@Override
public int hashCode() {
return Objects.hash(key, value);
}
}

View File

@@ -1,105 +0,0 @@
import de.dhbwstuttgart.parser.NullToken;
import de.dhbwstuttgart.parser.SyntaxTreeGenerator.GenericContext;
import de.dhbwstuttgart.parser.scope.JavaClassName;
import de.dhbwstuttgart.syntaxtree.GenericDeclarationList;
import de.dhbwstuttgart.syntaxtree.GenericTypeVar;
import de.dhbwstuttgart.syntaxtree.factory.ASTFactory;
import de.dhbwstuttgart.syntaxtree.type.*;
import de.dhbwstuttgart.target.generate.ASTToTargetAST;
import org.junit.Test;
import java.util.ArrayList;
import java.util.List;
import static org.junit.Assert.*;
public class GenericsParserTest {
@Test
public void testMethodNoGenerics() {
var signature = "()V";
var generics = ASTFactory.createGenerics(signature);
assertEquals(generics, new GenericDeclarationList(List.of(), new NullToken()));
}
@Test
public void testMethodSimpleGenerics() {
var signature = "<T:Ljava/lang/Object;>()V";
var generics = ASTFactory.createGenerics(signature);
assertEquals(generics, new GenericDeclarationList(
List.of(new GenericTypeVar("T", List.of(ASTToTargetAST.OBJECT), new NullToken(), new NullToken())), new NullToken())
);
}
@Test
public void testMethodExtends() {
var signature = "<T:Ljava/lang/Class<TT;>;>()V";
var generics = ASTFactory.createGenerics(signature);
assertEquals(generics, new GenericDeclarationList(
List.of(new GenericTypeVar("T", List.of(
new RefType(new JavaClassName("java.lang.Class"), List.of(new GenericRefType("T", new NullToken())), new NullToken())),
new NullToken(), new NullToken())), new NullToken()
)
);
}
@Test
public void testMethodVariance() {
var signature = "<T:Ljava/lang/Class<+TT;>;>()V";
var generics = ASTFactory.createGenerics(signature);
assertEquals(generics, new GenericDeclarationList(
List.of(new GenericTypeVar("T", List.of(
new RefType(new JavaClassName("java.lang.Class"), List.of(
new ExtendsWildcardType(new GenericRefType("T", new NullToken()), new NullToken())
), new NullToken())),
new NullToken(), new NullToken())),
new NullToken())
);
}
@Test
public void testMethodTypeVars() {
var signature = "<A:TB;B:LClassA;C:LClassB<TA;>;D:TB;>()V";
var generics = ASTFactory.createGenerics(signature);
assertEquals(generics, new GenericDeclarationList(
List.of(
new GenericTypeVar("A", List.of(new GenericRefType("B", new NullToken())), new NullToken(), new NullToken()),
new GenericTypeVar("B", List.of(new RefType(new JavaClassName("ClassA"), new NullToken())), new NullToken(), new NullToken()),
new GenericTypeVar("C", List.of(new RefType(new JavaClassName("ClassB"),
List.of(new GenericRefType("A", new NullToken())),
new NullToken())), new NullToken(), new NullToken()
),
new GenericTypeVar("D", List.of(new GenericRefType("B", new NullToken())), new NullToken(), new NullToken())
),
new NullToken()
));
}
@Test
public void testMethodComplex() {
var signature = "<T:LClassA<+TT;LClassB<+LClassA;-LClassC<LClassA;>;>;>;U:LClassC<LClassC;>;>()V";
var generics = ASTFactory.createGenerics(signature);
assertEquals(generics, new GenericDeclarationList(
List.of(new GenericTypeVar("T", List.of(
new RefType(new JavaClassName("ClassA"), List.of(
new ExtendsWildcardType(new GenericRefType("T", new NullToken()), new NullToken()),
new RefType(new JavaClassName("ClassB"), List.of(
new ExtendsWildcardType(new RefType(new JavaClassName("ClassA"), new NullToken()), new NullToken()),
new SuperWildcardType(
new RefType(new JavaClassName("ClassC"), List.of(
new RefType(new JavaClassName("ClassA"), new NullToken())
), new NullToken()), new NullToken())
), new NullToken())
), new NullToken())
), new NullToken(), new NullToken()),
new GenericTypeVar("U", List.of(
new RefType(new JavaClassName("ClassC"), List.of(
new RefType(new JavaClassName("ClassC"), new NullToken())
), new NullToken())
), new NullToken(), new NullToken())),
new NullToken()
));
}
}

View File

@@ -281,6 +281,7 @@ public class TestComplete {
@Test
public void scalarTest() throws Exception {
var classFiles = generateClassFiles(new ByteArrayClassLoader(), "Scalar.jav");
var scalar = classFiles.get("Scalar");
@@ -575,11 +576,6 @@ public class TestComplete {
assertEquals(fstArgm2, m2.getGenericReturnType());
}
@Test
public void testTXGenerics() throws Exception {
var classFiles = generateClassFiles(new ByteArrayClassLoader(), "TXGenerics.jav");
var instance = classFiles.get("TXGenerics").getDeclaredConstructor().newInstance();
}
@Test
public void typedIdTest() throws Exception {

View File

@@ -90,15 +90,16 @@ public class TestGenerics {
var generics = result.genericsResults.get(0);
assertEquals(0, generics.get(result.clazz).size());
assertEquals(1, generics.get(m).size());
assertEquals(2, generics.get(m).size());
assertEquals(2, generics.get(main).size());
var N = generics.getBounds(m.getParameterList().getParameterAt(0).getType(), result.clazz, m);
var N2 = generics.getBounds(m.getReturnType(), result.clazz, m);
var NChain = new BoundsList(new Bound(true, ASTToTargetAST.OBJECT));
assertEquals(N, N2);
assertEquals(N2, NChain);
assertEquals(N, NChain);
var Q = generics.getBounds(m.getReturnType(), result.clazz, m);
var QChain = new BoundsList(new Bound(true, TypePlaceholder.of("N")), new Bound(true, ASTToTargetAST.OBJECT));
assertEquals(Q, QChain);
var R = generics.getBounds(main.getParameterList().getParameterAt(0).getType(), result.clazz, main);
assertEquals(R, NChain);
@@ -303,18 +304,17 @@ public class TestGenerics {
var main = result.findMethod("main");
var generics = result.genericsResults.get(0);
var O = generics.getBounds(id.getReturnType(), result.clazz, id);
var O2 = generics.getBounds(id.getParameterList().getParameterAt(0).getType(), result.clazz, id);
assertEquals(O, O2);
assertEquals(O2, new BoundsList(new Bound(true, ASTToTargetAST.OBJECT)));
var Q = generics.getBounds(id.getReturnType(), result.clazz, id);
var N = generics.getBounds(id.getParameterList().getParameterAt(0).getType(), result.clazz, id);
assertEquals(Q, new BoundsList(new Bound(true, ASTToTargetAST.OBJECT)));
assertEquals(N, new BoundsList(new Bound(true, TypePlaceholder.of("Q")), new Bound(true, ASTToTargetAST.OBJECT)));
// TODO Maybe test in other ways if the parameter generics equals the return generics
var S = generics.getBounds(main.getReturnType(), result.clazz, main);
var S2 = generics.getBounds(main.getParameterList().getParameterAt(0).getType(), result.clazz, main);
var T = generics.getBounds(main.getParameterList().getParameterAt(1).getType(), result.clazz, main);
assertEquals(S, S2);
assertEquals(S2, new BoundsList(new Bound(true, ASTToTargetAST.OBJECT)));
assertEquals(T, new BoundsList(new Bound(true, ASTToTargetAST.OBJECT)));
var Q2 = generics.getBounds(main.getReturnType(), result.clazz, main);
var R = generics.getBounds(main.getParameterList().getParameterAt(0).getType(), result.clazz, main);
var S = generics.getBounds(main.getParameterList().getParameterAt(1).getType(), result.clazz, main);
assertEquals(Q2, new BoundsList(new Bound(true, ASTToTargetAST.OBJECT)));
assertEquals(R, new BoundsList(new Bound(true, TypePlaceholder.of("Q")), new Bound(true, ASTToTargetAST.OBJECT)));
assertEquals(S, new BoundsList(new Bound(true, TypePlaceholder.of("Q")), new Bound(true, ASTToTargetAST.OBJECT)));
}
@Test

View File

@@ -7,7 +7,16 @@ import de.dhbwstuttgart.syntaxtree.visual.ASTPrinter;
import de.dhbwstuttgart.syntaxtree.visual.ASTTypePrinter;
import de.dhbwstuttgart.typedeployment.TypeInsert;
import de.dhbwstuttgart.typedeployment.TypeInsertFactory;
import de.dhbwstuttgart.typeinference.constraints.Constraint;
import de.dhbwstuttgart.typeinference.constraints.ConstraintSet;
import de.dhbwstuttgart.typeinference.constraints.Pair;
import de.dhbwstuttgart.typeinference.result.ResultSet;
import de.dhbwstuttgart.typeinference.unify.TypeUnify;
import de.dhbwstuttgart.typeinference.unify.UnifyResultModelParallel;
import de.dhbwstuttgart.typeinference.unify.UnifyTaskModelParallel;
import de.dhbwstuttgart.typeinference.unify.interfaces.IFiniteClosure;
import de.dhbwstuttgart.typeinference.unify.model.*;
import org.apache.commons.io.output.NullWriter;
import org.junit.Test;
import java.io.File;
@@ -24,7 +33,130 @@ import java.util.Set;
public class UnifyTest {
public static final String rootDirectory = System.getProperty("user.dir")+"/resources/javFiles/";
/*
@Test
public void smallUnifyTest(){
UnifyType type1 = new PlaceholderType("a");
UnifyType type2 = new ReferenceType("List", new TypeParams(new PlaceholderType("b")));
UnifyPair pair1 = new UnifyPair(type1, type2, PairOperator.SMALLERDOT);
type1 = new ReferenceType("List", new TypeParams(new PlaceholderType("c")));
type2 = new PlaceholderType("a");
UnifyPair pair2 = new UnifyPair(type1, type2, PairOperator.SMALLERDOT);
type1 = new ReferenceType("String");
type2 = new PlaceholderType("b");
UnifyPair pair3 = new UnifyPair(type1, type2, PairOperator.SMALLERDOT);
type1 = new ReferenceType("Integer");
type2 = new PlaceholderType("c");
UnifyPair pair4 = new UnifyPair(type1, type2, PairOperator.SMALLERDOT);
Set<UnifyPair> undConstraints = new HashSet<>();
undConstraints.add(pair1);
undConstraints.add(pair2);
undConstraints.add(pair3);
undConstraints.add(pair4);
List<Set<Constraint<UnifyPair>>> oderConstraints = new ArrayList<>();
Set<UnifyPair> constraints = new HashSet<>();
type1 = new ReferenceType("Object");
type2 = new ReferenceType("String");
constraints.add(new UnifyPair(type2, type1, PairOperator.SMALLER));
type1 = new ReferenceType("Number");
type2 = new ReferenceType("Integer");
constraints.add(new UnifyPair(type2, type1, PairOperator.SMALLER));
type1 = new ReferenceType("Object");
type2 = new ReferenceType("Number");
constraints.add(new UnifyPair(type2, type1, PairOperator.SMALLER));
/* type1 = new ReferenceType("AbstractList", new TypeParams(new PlaceholderType("X")));
type2 = new ReferenceType("List", new TypeParams(new PlaceholderType("X")));
constraints.add(new UnifyPair(type1, type2, PairOperator.SMALLER));
type1 = new ReferenceType("Object");
type2 = new ReferenceType("AbstractList", new TypeParams(new PlaceholderType("X")));
constraints.add(new UnifyPair(type1, type2, PairOperator.SMALLER));*/
type1 = new ReferenceType("AbstractList", new PlaceholderType("X"));
type2 = new ReferenceType("List", new PlaceholderType("X"));
constraints.add(new UnifyPair(type2, type1, PairOperator.SMALLER));
type1 = new ReferenceType("Object");
type2 = new ReferenceType("AbstractList", new PlaceholderType("X"));
constraints.add(new UnifyPair(type2, type1, PairOperator.SMALLER));
IFiniteClosure finiteClosure = new FiniteClosure(constraints, new NullWriter());
TypeUnify unifyAlgo = new TypeUnify();
ConstraintSet< Pair> cons = new ConstraintSet<>();
UnifyResultModelParallel urm = new UnifyResultModelParallel(cons, finiteClosure);
UnifyTaskModelParallel tasks = new UnifyTaskModelParallel();
Set<Set<UnifyPair>> solution = unifyAlgo.unify(undConstraints, oderConstraints, finiteClosure, new NullWriter(), false, urm, tasks);
System.out.println(solution.size());
}
private UnifyPair genPairListOfInteger(String name){
UnifyType type1 = new PlaceholderType(name);
UnifyType type2 = new ReferenceType("List", new TypeParams(new ReferenceType("Integer")));
UnifyPair pair1 = new UnifyPair(type2, type1, PairOperator.SMALLERDOT);
return pair1;
}
private UnifyPair genPairListOfString(String name){
PlaceholderType type1 = new PlaceholderType(name);
UnifyType type2 = new ReferenceType("List", new TypeParams(new ReferenceType("String")));
UnifyPair pair1 = new UnifyPair(type2, type1, PairOperator.SMALLERDOT);
return pair1;
}
@Test
public void unifyTest(){
UnifyType type1;
UnifyType type2;
Set<UnifyPair> undConstraints = new HashSet<>();
undConstraints.add(genPairListOfInteger("a"));
undConstraints.add(genPairListOfString("a"));
undConstraints.add(genPairListOfInteger("b"));
undConstraints.add(genPairListOfString("b"));
undConstraints.add(genPairListOfInteger("c"));
undConstraints.add(genPairListOfString("c"));
undConstraints.add(genPairListOfInteger("d"));
undConstraints.add(genPairListOfString("d"));
undConstraints.add(genPairListOfInteger("e"));
undConstraints.add(genPairListOfString("e"));
undConstraints.add(genPairListOfInteger("e1"));
undConstraints.add(genPairListOfString("e1"));
undConstraints.add(genPairListOfInteger("e2"));
undConstraints.add(genPairListOfString("e2"));
undConstraints.add(genPairListOfInteger("e3"));
undConstraints.add(genPairListOfString("e3"));
List<Set<Constraint<UnifyPair>>> oderConstraints = new ArrayList<>();
Set<UnifyPair> constraints = new HashSet<>();
type1 = new ReferenceType("Object");
type2 = new ReferenceType("List", new TypeParams(new PlaceholderType("X")));
constraints.add(new UnifyPair(type2, type1, PairOperator.SMALLER));
type1 = new ReferenceType("Object");
type2 = new ReferenceType("Integer");
constraints.add(new UnifyPair(type2, type1, PairOperator.SMALLER));
type1 = new ReferenceType("Object");
type2 = new ReferenceType("String");
constraints.add(new UnifyPair(type2, type1, PairOperator.SMALLER));
IFiniteClosure finiteClosure = new FiniteClosure(constraints, new NullWriter());
TypeUnify unifyAlgo = new TypeUnify();
ConstraintSet< Pair> cons = new ConstraintSet<>();
UnifyResultModelParallel urm = new UnifyResultModelParallel(cons, finiteClosure);
UnifyTaskModelParallel tasks = new UnifyTaskModelParallel();
Set<Set<UnifyPair>> solution = unifyAlgo.unify(undConstraints, oderConstraints, finiteClosure, new NullWriter(), false, urm, tasks);
System.out.println(solution.size());
System.out.println(solution);
}
/*
@Test
public void finiteClosure() throws IOException, ClassNotFoundException {
execute(new File(rootDirectory+"fc.jav"));