Compare commits
20 Commits
targetByte
...
refactorTo
Author | SHA1 | Date | |
---|---|---|---|
|
669c778af8 | ||
|
5071406b3f | ||
|
9d2d076215 | ||
|
6262c9434c | ||
|
59c5e48201 | ||
|
1cf1c99e72 | ||
|
5c60918c47 | ||
|
a0367d5464 | ||
|
722d897d4b | ||
|
e2d76d314a | ||
|
cd5fbac987 | ||
|
67df9aa262 | ||
|
5b970f9359 | ||
|
1b5eacf921 | ||
|
a35e69f878 | ||
|
643f7c0220 | ||
|
24f1b507c4 | ||
|
a4cc4cc357 | ||
|
e80e2db26c | ||
|
4c0fb34c00 |
@ -592,7 +592,6 @@ public class BytecodeGenMethod implements StatementVisitor {
|
|||||||
this.lamCounter++;
|
this.lamCounter++;
|
||||||
|
|
||||||
String typeErasure = createDescriptorWithTypeErasure(lambdaExpression);
|
String typeErasure = createDescriptorWithTypeErasure(lambdaExpression);
|
||||||
//ToDo Etienne: Double Check
|
|
||||||
RefTypeOrTPHOrWildcardOrGeneric returnType = resolver.resolve(lambdaExpression.getReturnType());
|
RefTypeOrTPHOrWildcardOrGeneric returnType = resolver.resolve(lambdaExpression.getReturnType());
|
||||||
List<RefTypeOrTPHOrWildcardOrGeneric> argumentTypes = lambdaExpression
|
List<RefTypeOrTPHOrWildcardOrGeneric> argumentTypes = lambdaExpression
|
||||||
.params
|
.params
|
||||||
@ -828,7 +827,6 @@ public class BytecodeGenMethod implements StatementVisitor {
|
|||||||
} else if(!helper.isInCurrPkg(clazz)){
|
} else if(!helper.isInCurrPkg(clazz)){
|
||||||
if(clazz.contains(CONSTANTS.$$)) {
|
if(clazz.contains(CONSTANTS.$$)) {
|
||||||
mDesc = helper.getDescriptorOfApplyMethod(methCallType);
|
mDesc = helper.getDescriptorOfApplyMethod(methCallType);
|
||||||
//ToDo Etienne: Double Check
|
|
||||||
RefTypeOrTPHOrWildcardOrGeneric returnType = resolver.resolve(methodCall.getType());
|
RefTypeOrTPHOrWildcardOrGeneric returnType = resolver.resolve(methodCall.getType());
|
||||||
List<RefTypeOrTPHOrWildcardOrGeneric> argumentTypes = methodCall
|
List<RefTypeOrTPHOrWildcardOrGeneric> argumentTypes = methodCall
|
||||||
.arglist
|
.arglist
|
||||||
|
@ -153,7 +153,6 @@ public class DescriptorToString implements DescriptorVisitor, CONSTANTS {
|
|||||||
return desc;
|
return desc;
|
||||||
}
|
}
|
||||||
|
|
||||||
//ToDo Etienne: ändern
|
|
||||||
@Override
|
@Override
|
||||||
public String visit(Lambda lambdaExpression) {
|
public String visit(Lambda lambdaExpression) {
|
||||||
String desc = "(";
|
String desc = "(";
|
||||||
|
@ -45,6 +45,8 @@ public class TypeToDescriptor implements TypeVisitor<String>{
|
|||||||
//throw new NotImplementedException();
|
//throw new NotImplementedException();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//ToDo Etienne: bin der Meinung hier müsste immer der Descriptor der extends-Schranke sein, z.b. <T> => Ljava/lang/Object; oder <T extends String> => Ljava/lang/String;
|
||||||
|
//Tests sind aber damit grün?! => Fehler in Tests schon vorher aufgefallen und gut möglich!
|
||||||
@Override
|
@Override
|
||||||
public String visit(GenericRefType genericRefType) {
|
public String visit(GenericRefType genericRefType) {
|
||||||
return genericRefType.getParsedName().replace(".", "/");
|
return genericRefType.getParsedName().replace(".", "/");
|
||||||
|
@ -12,27 +12,30 @@ import org.objectweb.asm.ClassWriter;
|
|||||||
import org.objectweb.asm.MethodVisitor;
|
import org.objectweb.asm.MethodVisitor;
|
||||||
import org.objectweb.asm.Type;
|
import org.objectweb.asm.Type;
|
||||||
|
|
||||||
|
import javax.annotation.Nonnull;
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.FileOutputStream;
|
import java.io.FileOutputStream;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.Objects;
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
import java.util.stream.Stream;
|
import java.util.stream.Stream;
|
||||||
|
|
||||||
import static org.objectweb.asm.Opcodes.*;
|
import static org.objectweb.asm.Opcodes.*;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* //ToDo beschreiben
|
* Represents a Singleton-Service implementation for the {@link FunNUtilities} interface.
|
||||||
*
|
*
|
||||||
* @since Studienarbeit Type Erasure
|
* @since Studienarbeit Type Erasure
|
||||||
* @author etiennezink
|
* @author etiennezink
|
||||||
*/
|
*/
|
||||||
public class FunNGenerator implements FunNUtilities{
|
public final class FunNGenerator implements FunNUtilities{
|
||||||
|
|
||||||
private static FunNGenerator funNGenerator = new FunNGenerator();
|
private static final FunNGenerator funNGenerator = new FunNGenerator();
|
||||||
|
|
||||||
public static FunNGenerator getInstance(){
|
/**
|
||||||
return funNGenerator;
|
* @return the Singleton instance for {@link FunNGenerator}
|
||||||
}
|
*/
|
||||||
|
public static FunNUtilities getInstance(){ return funNGenerator; }
|
||||||
|
|
||||||
private final String argumentGenericBase = "T";
|
private final String argumentGenericBase = "T";
|
||||||
private final String returnGeneric = "R";
|
private final String returnGeneric = "R";
|
||||||
@ -43,9 +46,7 @@ public class FunNGenerator implements FunNUtilities{
|
|||||||
private final RefType objectRefType = new RefType(new JavaClassName(objectSuperType), null);
|
private final RefType objectRefType = new RefType(new JavaClassName(objectSuperType), null);
|
||||||
private final String objectSignature = applySignature(objectRefType);
|
private final String objectSignature = applySignature(objectRefType);
|
||||||
|
|
||||||
private String applyDescriptor(RefTypeOrTPHOrWildcardOrGeneric a) { return a.acceptTV(new TypeToDescriptor(true)); }
|
private FunNGenerator(){}
|
||||||
private String applySignature(RefTypeOrTPHOrWildcardOrGeneric a) { return a.acceptTV(new TypeToSignature(true)); }
|
|
||||||
private String applyNameDescriptor(RefTypeOrTPHOrWildcardOrGeneric a){ return a instanceof TypePlaceholder ? "LTPH;" : String.format("L%s;", applyDescriptor(a)); }
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public byte[] generateSuperBytecode(int numberArguments) {
|
public byte[] generateSuperBytecode(int numberArguments) {
|
||||||
@ -55,11 +56,11 @@ public class FunNGenerator implements FunNUtilities{
|
|||||||
|
|
||||||
for (int currentParameter = 1; currentParameter <= numberArguments; currentParameter++){
|
for (int currentParameter = 1; currentParameter <= numberArguments; currentParameter++){
|
||||||
superFunNClassSignature.append(String.format("%s%d:%s",argumentGenericBase, currentParameter, objectSignature));
|
superFunNClassSignature.append(String.format("%s%d:%s",argumentGenericBase, currentParameter, objectSignature));
|
||||||
superFunNMethodSignature.append(String.format("T%s;", applySignature( new GenericRefType(argumentGenericBase + currentParameter, null))));
|
superFunNMethodSignature.append(applySignature( new GenericRefType(argumentGenericBase + currentParameter, null)));
|
||||||
superFunNMethodDescriptor.append(objectSignature);
|
superFunNMethodDescriptor.append(objectSignature);
|
||||||
}
|
}
|
||||||
superFunNClassSignature.append(String.format("%s:%s>%s", returnGeneric, objectSignature, objectSignature));
|
superFunNClassSignature.append(String.format("%s:%s>%s", returnGeneric, objectSignature, objectSignature));
|
||||||
superFunNMethodSignature.append(String.format(")T%s;", applySignature(new GenericRefType(returnGeneric, null))));
|
superFunNMethodSignature.append(String.format(")%s", applySignature(new GenericRefType(returnGeneric, null))));
|
||||||
superFunNMethodDescriptor.append(String.format(")%s", objectSignature));
|
superFunNMethodDescriptor.append(String.format(")%s", objectSignature));
|
||||||
|
|
||||||
ClassWriter classWriter = new ClassWriter(0);
|
ClassWriter classWriter = new ClassWriter(0);
|
||||||
@ -78,8 +79,12 @@ public class FunNGenerator implements FunNUtilities{
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public byte[] generateSpecializedBytecode(List<RefTypeOrTPHOrWildcardOrGeneric> argumentTypes, RefTypeOrTPHOrWildcardOrGeneric returnType) {
|
public byte[] generateSpecializedBytecode(List<RefTypeOrTPHOrWildcardOrGeneric> argumentTypes, RefTypeOrTPHOrWildcardOrGeneric returnType) {
|
||||||
|
Objects.requireNonNull(argumentTypes);
|
||||||
|
Objects.requireNonNull(returnType);
|
||||||
|
//generates a list of all params and substitutes the TPH
|
||||||
List<RefTypeOrTPHOrWildcardOrGeneric> parameters = Stream
|
List<RefTypeOrTPHOrWildcardOrGeneric> parameters = Stream
|
||||||
.concat(argumentTypes.stream(), Stream.of(returnType))
|
.concat(argumentTypes.stream(), Stream.of(returnType))
|
||||||
|
.map(this::substituteTPH)
|
||||||
.collect(Collectors.toList());
|
.collect(Collectors.toList());
|
||||||
RefType superFunN = new RefType(new JavaClassName(getSuperClassName(argumentTypes.size())), parameters , null);
|
RefType superFunN = new RefType(new JavaClassName(getSuperClassName(argumentTypes.size())), parameters , null);
|
||||||
StringBuilder funNClassSignature = new StringBuilder(objectSignature + (superFunN.acceptTV(new TypeToSignature(false))));
|
StringBuilder funNClassSignature = new StringBuilder(objectSignature + (superFunN.acceptTV(new TypeToSignature(false))));
|
||||||
@ -87,16 +92,11 @@ public class FunNGenerator implements FunNUtilities{
|
|||||||
|
|
||||||
String genericSignature = "<";
|
String genericSignature = "<";
|
||||||
for (RefTypeOrTPHOrWildcardOrGeneric typeArgument : parameters) {
|
for (RefTypeOrTPHOrWildcardOrGeneric typeArgument : parameters) {
|
||||||
//ToDo Etienne: Refactor
|
|
||||||
if (typeArgument instanceof GenericRefType){
|
if (typeArgument instanceof GenericRefType){
|
||||||
GenericRefType generic = (GenericRefType) typeArgument;
|
GenericRefType generic = (GenericRefType) typeArgument;
|
||||||
if(genericSignature.contains(generic.getParsedName())) continue;
|
String signatureOfArgument = generic.getParsedName();
|
||||||
genericSignature += String.format("%s:%s", generic.getParsedName(), applyDescriptor(generic));
|
if(genericSignature.contains(signatureOfArgument)) continue;
|
||||||
containsGeneric = true;
|
genericSignature += String.format("%s:%s", signatureOfArgument, objectSignature);
|
||||||
} else if(typeArgument instanceof TypePlaceholder){
|
|
||||||
TypePlaceholder placeholder = (TypePlaceholder) typeArgument;
|
|
||||||
if(genericSignature.contains(applySignature(placeholder).substring(1))) continue;
|
|
||||||
genericSignature += String.format("%s:%s", applySignature(placeholder).substring(1), objectSignature);
|
|
||||||
containsGeneric = true;
|
containsGeneric = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -111,7 +111,9 @@ public class FunNGenerator implements FunNUtilities{
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String getSpecializedClassName(List<RefTypeOrTPHOrWildcardOrGeneric> argumentTypes, RefTypeOrTPHOrWildcardOrGeneric returnType) {
|
public String getSpecializedClassName(List<RefTypeOrTPHOrWildcardOrGeneric> argumentTypes, RefTypeOrTPHOrWildcardOrGeneric returnType) {
|
||||||
return String.format("Fun%d$$%s%s",
|
Objects.requireNonNull(argumentTypes);
|
||||||
|
Objects.requireNonNull(returnType);
|
||||||
|
return String.format("Fun%d$$$_$%s%s",
|
||||||
argumentTypes.size(),
|
argumentTypes.size(),
|
||||||
argumentTypes
|
argumentTypes
|
||||||
.stream()
|
.stream()
|
||||||
@ -124,16 +126,21 @@ public class FunNGenerator implements FunNUtilities{
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String getSpecializedDescriptor(List<RefTypeOrTPHOrWildcardOrGeneric> argumentTypes, RefTypeOrTPHOrWildcardOrGeneric returnType) {
|
public String getSpecializedDescriptor(List<RefTypeOrTPHOrWildcardOrGeneric> argumentTypes, RefTypeOrTPHOrWildcardOrGeneric returnType) {
|
||||||
return applyDescriptor(new RefType(new JavaClassName(getSpecializedClassName(argumentTypes, returnType)), null));
|
Objects.requireNonNull(argumentTypes);
|
||||||
|
Objects.requireNonNull(returnType);
|
||||||
|
return applyDescriptor(getSpecializedFunNRefType(argumentTypes, returnType));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String getSpecializedSignature(List<RefTypeOrTPHOrWildcardOrGeneric> argumentTypes, RefTypeOrTPHOrWildcardOrGeneric returnType) {
|
public String getSpecializedSignature(List<RefTypeOrTPHOrWildcardOrGeneric> argumentTypes, RefTypeOrTPHOrWildcardOrGeneric returnType) {
|
||||||
return applySignature(new RefType(new JavaClassName(getSpecializedClassName(argumentTypes, returnType)), null));
|
Objects.requireNonNull(argumentTypes);
|
||||||
|
Objects.requireNonNull(returnType);
|
||||||
|
return applySignature(getSpecializedFunNRefType(argumentTypes, returnType));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<RefTypeOrTPHOrWildcardOrGeneric> getArguments(List<RefTypeOrTPHOrWildcardOrGeneric> list) {
|
public List<RefTypeOrTPHOrWildcardOrGeneric> getArguments(List<RefTypeOrTPHOrWildcardOrGeneric> list) {
|
||||||
|
Objects.requireNonNull(list);
|
||||||
return list
|
return list
|
||||||
.stream()
|
.stream()
|
||||||
.limit(Math.max(0, list.size() - 1))
|
.limit(Math.max(0, list.size() - 1))
|
||||||
@ -142,8 +149,33 @@ public class FunNGenerator implements FunNUtilities{
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public RefTypeOrTPHOrWildcardOrGeneric getReturnType(List<RefTypeOrTPHOrWildcardOrGeneric> list) {
|
public RefTypeOrTPHOrWildcardOrGeneric getReturnType(List<RefTypeOrTPHOrWildcardOrGeneric> list) {
|
||||||
if(list.size() == 0)
|
Objects.requireNonNull(list);
|
||||||
throw new IndexOutOfBoundsException();
|
if(list.size() == 0) return null;
|
||||||
return list.get(list.size() - 1);
|
return list.get(list.size() - 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private String applyDescriptor(RefTypeOrTPHOrWildcardOrGeneric a) { return a.acceptTV(new TypeToDescriptor(true)); }
|
||||||
|
private String applySignature(RefTypeOrTPHOrWildcardOrGeneric a) { return a.acceptTV(new TypeToSignature(true)); }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param a
|
||||||
|
* @return the name for the type {@code a} which should be used in the specialized name for FunN.
|
||||||
|
*/
|
||||||
|
private String applyNameDescriptor(RefTypeOrTPHOrWildcardOrGeneric a){ return a instanceof TypePlaceholder ? "LTPH;" : String.format("L%s;", applyDescriptor(a)); }
|
||||||
|
|
||||||
|
private RefTypeOrTPHOrWildcardOrGeneric substituteTPH(RefTypeOrTPHOrWildcardOrGeneric t) {
|
||||||
|
if (t instanceof TypePlaceholder) {
|
||||||
|
TypePlaceholder tph = (TypePlaceholder) t;
|
||||||
|
return new GenericRefType(tph.getName()+"$", t.getOffset());
|
||||||
|
}
|
||||||
|
return t;
|
||||||
|
}
|
||||||
|
private RefType getSpecializedFunNRefType(List<RefTypeOrTPHOrWildcardOrGeneric> argumentTypes, RefTypeOrTPHOrWildcardOrGeneric returnType){
|
||||||
|
return new RefType(new JavaClassName(getSpecializedClassName(argumentTypes, returnType)),
|
||||||
|
Stream
|
||||||
|
.concat(argumentTypes.stream(), Stream.of(returnType))
|
||||||
|
.filter(t -> t instanceof GenericRefType ||
|
||||||
|
t instanceof TypePlaceholder)
|
||||||
|
.collect(Collectors.toList()),null);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -3,25 +3,81 @@ package de.dhbwstuttgart.bytecode.funN;
|
|||||||
import de.dhbwstuttgart.bytecode.utilities.CONSTANTS;
|
import de.dhbwstuttgart.bytecode.utilities.CONSTANTS;
|
||||||
import de.dhbwstuttgart.syntaxtree.type.RefTypeOrTPHOrWildcardOrGeneric;
|
import de.dhbwstuttgart.syntaxtree.type.RefTypeOrTPHOrWildcardOrGeneric;
|
||||||
|
|
||||||
|
import javax.annotation.Nonnull;
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.FileOutputStream;
|
import java.io.FileOutputStream;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Interface which represents the functionality for specifying and generating the specified functional types (FunN).
|
||||||
|
*
|
||||||
|
* @since Studienarbeit Type Erasure
|
||||||
|
* @author etiennezink
|
||||||
|
*/
|
||||||
public interface FunNUtilities {
|
public interface FunNUtilities {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param numberArguments (excluding the return type!)
|
||||||
|
* @return the bytecode for the super FunN-interface
|
||||||
|
*/
|
||||||
byte[] generateSuperBytecode(int numberArguments);
|
byte[] generateSuperBytecode(int numberArguments);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param numberArguments (excluding the return type!)
|
||||||
|
* @return the name for the super FunN-interface
|
||||||
|
*/
|
||||||
String getSuperClassName(int numberArguments);
|
String getSuperClassName(int numberArguments);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param argumentTypes (excluding the return type!)
|
||||||
|
* @param returnType
|
||||||
|
* @return the bytecode for the specialized FunN-interface
|
||||||
|
*/
|
||||||
byte[] generateSpecializedBytecode(List<RefTypeOrTPHOrWildcardOrGeneric> argumentTypes, RefTypeOrTPHOrWildcardOrGeneric returnType);
|
byte[] generateSpecializedBytecode(List<RefTypeOrTPHOrWildcardOrGeneric> argumentTypes, RefTypeOrTPHOrWildcardOrGeneric returnType);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param argumentTypes (excluding the return type!)
|
||||||
|
* @param returnType
|
||||||
|
* @return the name for the specialized FunN-interface
|
||||||
|
*/
|
||||||
String getSpecializedClassName(List<RefTypeOrTPHOrWildcardOrGeneric> argumentTypes, RefTypeOrTPHOrWildcardOrGeneric returnType);
|
String getSpecializedClassName(List<RefTypeOrTPHOrWildcardOrGeneric> argumentTypes, RefTypeOrTPHOrWildcardOrGeneric returnType);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param argumentTypes (excluding the return type!)
|
||||||
|
* @param returnType
|
||||||
|
* @return the descriptor for a specialized FunN-interface.
|
||||||
|
*/
|
||||||
String getSpecializedDescriptor(List<RefTypeOrTPHOrWildcardOrGeneric> argumentTypes, RefTypeOrTPHOrWildcardOrGeneric returnType);
|
String getSpecializedDescriptor(List<RefTypeOrTPHOrWildcardOrGeneric> argumentTypes, RefTypeOrTPHOrWildcardOrGeneric returnType);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param argumentTypes (excluding the return type!)
|
||||||
|
* @param returnType
|
||||||
|
* @return the signature for a specialized FunN-interface.
|
||||||
|
*/
|
||||||
String getSpecializedSignature(List<RefTypeOrTPHOrWildcardOrGeneric> argumentTypes, RefTypeOrTPHOrWildcardOrGeneric returnType);
|
String getSpecializedSignature(List<RefTypeOrTPHOrWildcardOrGeneric> argumentTypes, RefTypeOrTPHOrWildcardOrGeneric returnType);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param list containing type arguments and the return type.
|
||||||
|
* @return a {@link List} containing only the arguments of the specialized FunN-interface.
|
||||||
|
*/
|
||||||
List<RefTypeOrTPHOrWildcardOrGeneric> getArguments(List<RefTypeOrTPHOrWildcardOrGeneric> list);
|
List<RefTypeOrTPHOrWildcardOrGeneric> getArguments(List<RefTypeOrTPHOrWildcardOrGeneric> list);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param list containing type arguments and the return type.
|
||||||
|
* @return the return type of the {@code list} (last member)
|
||||||
|
*/
|
||||||
RefTypeOrTPHOrWildcardOrGeneric getReturnType(List<RefTypeOrTPHOrWildcardOrGeneric> list);
|
RefTypeOrTPHOrWildcardOrGeneric getReturnType(List<RefTypeOrTPHOrWildcardOrGeneric> list);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Should be refactored into a central API.
|
||||||
|
*
|
||||||
|
* @param className
|
||||||
|
* @param bytecode
|
||||||
|
* @param directory
|
||||||
|
* @return {@code true} iff the file could be generated and {@code false} if not
|
||||||
|
*/
|
||||||
@Deprecated
|
@Deprecated
|
||||||
public static boolean writeClassFile(String className, byte[] bytecode, File directory) {
|
static boolean writeClassFile(String className, byte[] bytecode, File directory) {
|
||||||
try (FileOutputStream output = new FileOutputStream(new File(directory , className + CONSTANTS.EXTENSIONCLASS))){
|
try (FileOutputStream output = new FileOutputStream(new File(directory , className + CONSTANTS.EXTENSIONCLASS))){
|
||||||
output.write(bytecode);
|
output.write(bytecode);
|
||||||
output.flush();
|
output.flush();
|
||||||
@ -31,6 +87,4 @@ public interface FunNUtilities {
|
|||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -102,9 +102,20 @@ public class TypeToSignature implements TypeVisitor<String> {
|
|||||||
return sig;
|
return sig;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Changed that the correct signature is returned:
|
||||||
|
* returns now T...; expect of only ...
|
||||||
|
* where ... is {@code genericRefType.getParsedName()}
|
||||||
|
*
|
||||||
|
* @since Studienarbeit Type Erasure
|
||||||
|
* @author etiennezink
|
||||||
|
*
|
||||||
|
* @param genericRefType
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
@Override
|
@Override
|
||||||
public String visit(GenericRefType genericRefType) {
|
public String visit(GenericRefType genericRefType) {
|
||||||
return genericRefType.getParsedName().replace(".", "/");
|
return String.format("T%s;", genericRefType.getParsedName()).replace(".", "/");
|
||||||
}
|
}
|
||||||
|
|
||||||
private Optional<GenericsGeneratorResult> getEqualTPHFromClassConstraints(List<GenericsGeneratorResult> listOfConstraints, String tph) {
|
private Optional<GenericsGeneratorResult> getEqualTPHFromClassConstraints(List<GenericsGeneratorResult> listOfConstraints, String tph) {
|
||||||
|
@ -26,7 +26,6 @@ public class Resolver {
|
|||||||
return resultSet.resolveType(type).resolvedType.acceptTV(new TypeToDescriptor());
|
return resultSet.resolveType(type).resolvedType.acceptTV(new TypeToDescriptor());
|
||||||
}
|
}
|
||||||
|
|
||||||
//ToDo Etienne: Check ob benötigt
|
|
||||||
public RefTypeOrTPHOrWildcardOrGeneric resolve(RefTypeOrTPHOrWildcardOrGeneric type) {
|
public RefTypeOrTPHOrWildcardOrGeneric resolve(RefTypeOrTPHOrWildcardOrGeneric type) {
|
||||||
return resultSet.resolveType(type).resolvedType;
|
return resultSet.resolveType(type).resolvedType;
|
||||||
}
|
}
|
||||||
|
@ -4,6 +4,8 @@ import de.dhbwstuttgart.syntaxtree.ASTVisitor;
|
|||||||
import de.dhbwstuttgart.typeinference.result.ResultSetVisitor;
|
import de.dhbwstuttgart.typeinference.result.ResultSetVisitor;
|
||||||
import org.antlr.v4.runtime.Token;
|
import org.antlr.v4.runtime.Token;
|
||||||
|
|
||||||
|
import java.util.Objects;
|
||||||
|
|
||||||
public class GenericRefType extends RefTypeOrTPHOrWildcardOrGeneric
|
public class GenericRefType extends RefTypeOrTPHOrWildcardOrGeneric
|
||||||
{
|
{
|
||||||
private String name;
|
private String name;
|
||||||
@ -33,12 +35,20 @@ public class GenericRefType extends RefTypeOrTPHOrWildcardOrGeneric
|
|||||||
visitor.visit(this);
|
visitor.visit(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @since Studienarbeit Type Erasure
|
||||||
|
* @author etiennezink
|
||||||
|
*
|
||||||
|
* @param o
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
@Override
|
@Override
|
||||||
public boolean equals(Object o) {
|
public boolean equals(Object o) {
|
||||||
// TODO Auto-generated method stub
|
if((! (o instanceof GenericRefType))) return false;
|
||||||
return false;
|
GenericRefType genericRefType = (GenericRefType) o;
|
||||||
}
|
return getParsedName().equals(genericRefType.getParsedName()) &&
|
||||||
|
Objects.equals(getOffset(), genericRefType.getOffset());
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String toString()
|
public String toString()
|
||||||
|
@ -20,7 +20,8 @@ public class ASTToTargetAST {
|
|||||||
public TargetClass convert(ClassOrInterface input, Map<TypePlaceholder, TargetType> sigma){
|
public TargetClass convert(ClassOrInterface input, Map<TypePlaceholder, TargetType> sigma){
|
||||||
List<TargetConstructor> targetConstructors = new ArrayList<>();
|
List<TargetConstructor> targetConstructors = new ArrayList<>();
|
||||||
//TODO constructor conversion -> also reduce syntactic sugar
|
//TODO constructor conversion -> also reduce syntactic sugar
|
||||||
return new TargetClass(input.getModifiers(),input.getClassName().toString(), sigma.get(input.getSuperClass()),
|
return new TargetClass(input.getModifiers(),input.getClassName().toString(), null,
|
||||||
|
sigma.get(input.getSuperClass()),
|
||||||
input.getSuperInterfaces().stream().map(it -> sigma.get(it)).collect(Collectors.toList()),
|
input.getSuperInterfaces().stream().map(it -> sigma.get(it)).collect(Collectors.toList()),
|
||||||
targetConstructors,
|
targetConstructors,
|
||||||
input.getFieldDecl().stream().map(it -> convert(it, sigma)).collect(Collectors.toList()),
|
input.getFieldDecl().stream().map(it -> convert(it, sigma)).collect(Collectors.toList()),
|
||||||
@ -42,7 +43,7 @@ public class ASTToTargetAST {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private TargetField convert(Field input, Map<TypePlaceholder, TargetType> sigma) {
|
private TargetField convert(Field input, Map<TypePlaceholder, TargetType> sigma) {
|
||||||
return null;
|
return new TargetField(convert(input.getType(), sigma), input.getName());
|
||||||
}
|
}
|
||||||
|
|
||||||
private TargetType convert(RefTypeOrTPHOrWildcardOrGeneric input, Map<TypePlaceholder, TargetType> sigma) {
|
private TargetType convert(RefTypeOrTPHOrWildcardOrGeneric input, Map<TypePlaceholder, TargetType> sigma) {
|
||||||
|
@ -0,0 +1,7 @@
|
|||||||
|
package de.dhbwstuttgart.target.tree;
|
||||||
|
|
||||||
|
import de.dhbwstuttgart.syntaxtree.type.GenericRefType;
|
||||||
|
import de.dhbwstuttgart.target.tree.type.TargetType;
|
||||||
|
|
||||||
|
public record GenericDeclaration(GenericRefType generic, TargetType bound) {
|
||||||
|
}
|
@ -5,6 +5,7 @@ import de.dhbwstuttgart.target.tree.type.TargetType;
|
|||||||
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
public record TargetClass(int modifiers, String qualifiedName, TargetType superType, List<TargetType> implementingInterfaces,
|
public record TargetClass(int modifiers, String qualifiedName, List<GenericDeclaration> generics, TargetType superType,
|
||||||
|
List<TargetType> implementingInterfaces,
|
||||||
List<TargetConstructor> constructors, List<TargetField> fields, List<TargetMethod> methods) {}
|
List<TargetConstructor> constructors, List<TargetField> fields, List<TargetMethod> methods) {}
|
||||||
|
|
||||||
|
@ -1,7 +1,9 @@
|
|||||||
package de.dhbwstuttgart.target.tree;
|
package de.dhbwstuttgart.target.tree;
|
||||||
|
|
||||||
|
import de.dhbwstuttgart.target.tree.expression.TargetBlock;
|
||||||
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
public record TargetConstructor(List<MethodParameter> parameterTypes) {
|
public record TargetConstructor(List<MethodParameter> parameterTypes, TargetBlock block) {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,7 +1,5 @@
|
|||||||
package de.dhbwstuttgart.target.tree.type;
|
package de.dhbwstuttgart.target.tree.type;
|
||||||
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
public record TargetExtendsWildcard(TargetType innerType) implements TargetType{
|
public record TargetExtendsWildcard(TargetType innerType) implements TargetType{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -4,7 +4,6 @@ import java.io.File;
|
|||||||
import java.lang.reflect.Method;
|
import java.lang.reflect.Method;
|
||||||
import java.net.URL;
|
import java.net.URL;
|
||||||
import java.net.URLClassLoader;
|
import java.net.URLClassLoader;
|
||||||
import java.util.function.Function;
|
|
||||||
|
|
||||||
import general.TestCleanUp;
|
import general.TestCleanUp;
|
||||||
import org.junit.*;
|
import org.junit.*;
|
||||||
@ -12,7 +11,8 @@ import de.dhbwstuttgart.core.JavaTXCompiler;
|
|||||||
import static org.junit.Assert.*;
|
import static org.junit.Assert.*;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* //ToDo Etienne: Beschreiben
|
* Test for the file {@code OLFun2.jav}.
|
||||||
|
* Tests if the expected overloading for the method {@code m} exists.
|
||||||
*
|
*
|
||||||
* @since Studienarbeit Type Erasure
|
* @since Studienarbeit Type Erasure
|
||||||
* @author etiennezink
|
* @author etiennezink
|
||||||
@ -24,13 +24,12 @@ public class OLFun2Test {
|
|||||||
private static ClassLoader loader;
|
private static ClassLoader loader;
|
||||||
private static Class<?> classToTest;
|
private static Class<?> classToTest;
|
||||||
private static Class<?> classFun1IntInt;
|
private static Class<?> classFun1IntInt;
|
||||||
|
private static Class<?> classFun1IntDouble;
|
||||||
private static Class<?> classFun1DoubleDouble;
|
private static Class<?> classFun1DoubleDouble;
|
||||||
private static Class<?> classFun1StringString;
|
private static Class<?> classFun1DoubleInt;
|
||||||
|
|
||||||
private static String generatedByteCodeDirectory = System.getProperty("user.dir") + "/src/test/resources/testBytecode/generatedBC/";
|
private static String generatedByteCodeDirectory = System.getProperty("user.dir") + "/src/test/resources/testBytecode/generatedBC/";
|
||||||
|
|
||||||
//ToDo Etienne: Nach Anpassung des Bytecode die Tests hinzufügen
|
|
||||||
//ToDo Etienne: Aufruf von m testen
|
|
||||||
@BeforeClass
|
@BeforeClass
|
||||||
public static void setUp() throws Exception {
|
public static void setUp() throws Exception {
|
||||||
path = System.getProperty("user.dir")+"/src/test/resources/bytecode/javFiles/OLFun2.jav";
|
path = System.getProperty("user.dir")+"/src/test/resources/bytecode/javFiles/OLFun2.jav";
|
||||||
@ -39,31 +38,42 @@ public class OLFun2Test {
|
|||||||
compiler.generateBytecode(generatedByteCodeDirectory);
|
compiler.generateBytecode(generatedByteCodeDirectory);
|
||||||
loader = new URLClassLoader(new URL[] {new URL("file://"+generatedByteCodeDirectory)});
|
loader = new URLClassLoader(new URL[] {new URL("file://"+generatedByteCodeDirectory)});
|
||||||
classToTest = loader.loadClass("OLFun2");
|
classToTest = loader.loadClass("OLFun2");
|
||||||
classFun1IntInt = loader.loadClass("Fun1$$Ljava$lang$Integer$_$Ljava$lang$Integer$_$");
|
classFun1IntInt = loader.loadClass("Fun1$$$_$Ljava$lang$Integer$_$Ljava$lang$Integer$_$");
|
||||||
classFun1DoubleDouble = loader.loadClass("Fun1$$Ljava$lang$Double$_$Ljava$lang$Double$_$");
|
classFun1IntDouble = loader.loadClass("Fun1$$$_$Ljava$lang$Integer$_$Ljava$lang$Double$_$");
|
||||||
classFun1StringString = loader.loadClass("Fun1$$Ljava$lang$String$_$Ljava$lang$String$_$");
|
classFun1DoubleDouble = loader.loadClass("Fun1$$$_$Ljava$lang$Double$_$Ljava$lang$Double$_$");
|
||||||
|
classFun1DoubleInt = loader.loadClass("Fun1$$$_$Ljava$lang$Double$_$Ljava$lang$Integer$_$");
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void mExistsWithInteger() throws Exception{
|
public void mExistsWithIntegerInteger() throws Exception{
|
||||||
Method m = classToTest.getDeclaredMethod("m", classFun1IntInt);
|
Method m = classToTest.getDeclaredMethod("m", classFun1IntInt);
|
||||||
assertNotNull(m);
|
assertNotNull(m);
|
||||||
|
assertEquals(Integer.class, m.getReturnType());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void mExistsWithDouble() throws Exception{
|
public void mExistsWithIntegerDouble() throws Exception{
|
||||||
|
Method m = classToTest.getDeclaredMethod("m", classFun1IntDouble);
|
||||||
|
assertNotNull(m);
|
||||||
|
assertEquals(Double.class, m.getReturnType());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void mExistsWithDoubleInteger() throws Exception{
|
||||||
|
Method m = classToTest.getDeclaredMethod("m", classFun1DoubleInt);
|
||||||
|
assertNotNull(m);
|
||||||
|
assertEquals(Integer.class, m.getReturnType());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void mExistsWithDoubleDouble() throws Exception{
|
||||||
Method m = classToTest.getDeclaredMethod("m", classFun1DoubleDouble);
|
Method m = classToTest.getDeclaredMethod("m", classFun1DoubleDouble);
|
||||||
assertNotNull(m);
|
assertNotNull(m);
|
||||||
|
assertEquals(Double.class, m.getReturnType());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@AfterClass
|
||||||
public void mExistsWithString() throws Exception{
|
public static void cleanUp() {
|
||||||
Method m = classToTest.getDeclaredMethod("m", classFun1StringString);
|
|
||||||
assertNotNull(m);
|
|
||||||
}
|
|
||||||
|
|
||||||
//@AfterClass
|
|
||||||
public static void cleanUp(){
|
|
||||||
TestCleanUp.cleanUpDirectory(new File(generatedByteCodeDirectory), f -> f.getName().contains(".class"));
|
TestCleanUp.cleanUpDirectory(new File(generatedByteCodeDirectory), f -> f.getName().contains(".class"));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -11,7 +11,8 @@ import de.dhbwstuttgart.core.JavaTXCompiler;
|
|||||||
import static org.junit.Assert.*;
|
import static org.junit.Assert.*;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* //ToDo Etienne: Beschreiben
|
* Test for the file {@code OLFun.jav}.
|
||||||
|
* Tests if the expected overloading for the method {@code m} exists.
|
||||||
*
|
*
|
||||||
* @since Studienarbeit Type Erasure
|
* @since Studienarbeit Type Erasure
|
||||||
* @author etiennezink
|
* @author etiennezink
|
||||||
@ -23,13 +24,14 @@ public class OLFunTest {
|
|||||||
private static ClassLoader loader;
|
private static ClassLoader loader;
|
||||||
private static Class<?> classToTest;
|
private static Class<?> classToTest;
|
||||||
private static Class<?> classFun1IntInt;
|
private static Class<?> classFun1IntInt;
|
||||||
|
private static Class<?> classFun1IntDouble;
|
||||||
private static Class<?> classFun1DoubleDouble;
|
private static Class<?> classFun1DoubleDouble;
|
||||||
private static Class<?> classFun1StringString;
|
private static Class<?> classFun1DoubleInt;
|
||||||
|
private static Class<?> classFun1StringInt;
|
||||||
|
private static Class<?> classFun1StringDouble;
|
||||||
|
|
||||||
private static String generatedByteCodeDirectory = System.getProperty("user.dir") + "/src/test/resources/testBytecode/generatedBC/";
|
private static String generatedByteCodeDirectory = System.getProperty("user.dir") + "/src/test/resources/testBytecode/generatedBC/";
|
||||||
|
|
||||||
//ToDo Etienne: Nach Anpassung des Bytecode die Tests hinzufügen
|
|
||||||
//ToDo Etienne: Aufruf von m testen
|
|
||||||
@BeforeClass
|
@BeforeClass
|
||||||
public static void setUp() throws Exception {
|
public static void setUp() throws Exception {
|
||||||
path = System.getProperty("user.dir")+"/src/test/resources/bytecode/javFiles/OLFun.jav";
|
path = System.getProperty("user.dir")+"/src/test/resources/bytecode/javFiles/OLFun.jav";
|
||||||
@ -38,30 +40,51 @@ public class OLFunTest {
|
|||||||
compiler.generateBytecode(generatedByteCodeDirectory);
|
compiler.generateBytecode(generatedByteCodeDirectory);
|
||||||
loader = new URLClassLoader(new URL[] {new URL("file://"+generatedByteCodeDirectory)});
|
loader = new URLClassLoader(new URL[] {new URL("file://"+generatedByteCodeDirectory)});
|
||||||
classToTest = loader.loadClass("OLFun");
|
classToTest = loader.loadClass("OLFun");
|
||||||
classFun1IntInt = loader.loadClass("Fun1$$Ljava$lang$Integer$_$Ljava$lang$Integer$_$");
|
classFun1IntInt = loader.loadClass("Fun1$$$_$Ljava$lang$Integer$_$Ljava$lang$Integer$_$");
|
||||||
classFun1DoubleDouble = loader.loadClass("Fun1$$Ljava$lang$Double$_$Ljava$lang$Double$_$");
|
classFun1IntDouble = loader.loadClass("Fun1$$$_$Ljava$lang$Integer$_$Ljava$lang$Double$_$");
|
||||||
classFun1StringString = loader.loadClass("Fun1$$Ljava$lang$String$_$Ljava$lang$String$_$");
|
classFun1DoubleDouble = loader.loadClass("Fun1$$$_$Ljava$lang$Double$_$Ljava$lang$Double$_$");
|
||||||
|
classFun1DoubleInt = loader.loadClass("Fun1$$$_$Ljava$lang$Double$_$Ljava$lang$Integer$_$");
|
||||||
|
classFun1StringInt = loader.loadClass("Fun1$$$_$Ljava$lang$String$_$Ljava$lang$Integer$_$");
|
||||||
|
classFun1StringDouble = loader.loadClass("Fun1$$$_$Ljava$lang$String$_$Ljava$lang$Double$_$");
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void mExistsWithInteger() throws Exception{
|
public void mExistsWithIntegerInteger() throws Exception{
|
||||||
Method m = classToTest.getDeclaredMethod("m", classFun1IntInt ,Integer.class);
|
Method m = classToTest.getDeclaredMethod("m", classFun1IntInt, Integer.class);
|
||||||
assertNotNull(m);
|
assertNotNull(m);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void mExistsWithDouble() throws Exception{
|
public void mExistsWithIntegerDouble() throws Exception{
|
||||||
Method m = classToTest.getDeclaredMethod("m", classFun1DoubleDouble ,Double.class);
|
Method m = classToTest.getDeclaredMethod("m", classFun1IntDouble, Integer.class);
|
||||||
assertNotNull(m);
|
assertNotNull(m);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void mExistsWithString() throws Exception{
|
public void mExistsWithDoubleInteger() throws Exception{
|
||||||
Method m = classToTest.getDeclaredMethod("m", classFun1StringString ,String.class);
|
Method m = classToTest.getDeclaredMethod("m", classFun1DoubleInt, Double.class);
|
||||||
assertNotNull(m);
|
assertNotNull(m);
|
||||||
}
|
}
|
||||||
|
|
||||||
//@AfterClass
|
@Test
|
||||||
|
public void mExistsWithDoubleDouble() throws Exception{
|
||||||
|
Method m = classToTest.getDeclaredMethod("m", classFun1DoubleDouble, Double.class);
|
||||||
|
assertNotNull(m);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void mExistsWithStringInteger() throws Exception{
|
||||||
|
Method m = classToTest.getDeclaredMethod("m", classFun1StringInt, String.class);
|
||||||
|
assertNotNull(m);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void mExistsWithStringDouble() throws Exception{
|
||||||
|
Method m = classToTest.getDeclaredMethod("m", classFun1StringDouble, String.class);
|
||||||
|
assertNotNull(m);
|
||||||
|
}
|
||||||
|
|
||||||
|
@AfterClass
|
||||||
public static void cleanUp(){
|
public static void cleanUp(){
|
||||||
TestCleanUp.cleanUpDirectory(new File(generatedByteCodeDirectory), f -> f.getName().contains(".class"));
|
TestCleanUp.cleanUpDirectory(new File(generatedByteCodeDirectory), f -> f.getName().contains(".class"));
|
||||||
}
|
}
|
||||||
|
248
src/test/java/bytecode/funN/FunNGeneratorTest.java
Normal file
248
src/test/java/bytecode/funN/FunNGeneratorTest.java
Normal file
@ -0,0 +1,248 @@
|
|||||||
|
package bytecode.funN;
|
||||||
|
|
||||||
|
import de.dhbwstuttgart.bytecode.funN.FunNGenerator;
|
||||||
|
import de.dhbwstuttgart.bytecode.funN.FunNUtilities;
|
||||||
|
import de.dhbwstuttgart.parser.scope.JavaClassName;
|
||||||
|
import de.dhbwstuttgart.syntaxtree.type.GenericRefType;
|
||||||
|
import de.dhbwstuttgart.syntaxtree.type.RefType;
|
||||||
|
import de.dhbwstuttgart.syntaxtree.type.TypePlaceholder;
|
||||||
|
import org.junit.BeforeClass;
|
||||||
|
import org.junit.Test;
|
||||||
|
import org.objectweb.asm.ClassWriter;
|
||||||
|
import org.objectweb.asm.Type;
|
||||||
|
|
||||||
|
import java.util.Arrays;
|
||||||
|
|
||||||
|
import static org.junit.Assert.*;
|
||||||
|
import static org.objectweb.asm.Opcodes.*;
|
||||||
|
|
||||||
|
public class FunNGeneratorTest {
|
||||||
|
|
||||||
|
static FunNUtilities funNGenerator;
|
||||||
|
static RefType voidType;
|
||||||
|
static RefType integerType;
|
||||||
|
static GenericRefType genericT;
|
||||||
|
static TypePlaceholder tph;
|
||||||
|
|
||||||
|
@BeforeClass
|
||||||
|
public static void setUp(){
|
||||||
|
|
||||||
|
funNGenerator = FunNGenerator.getInstance();
|
||||||
|
voidType = new RefType(new JavaClassName(Type.getInternalName(Void.class)), null);
|
||||||
|
integerType = new RefType(new JavaClassName(Type.getInternalName(Integer.class)), null);
|
||||||
|
genericT = new GenericRefType("T", null);
|
||||||
|
tph = TypePlaceholder.fresh(null);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void superClassName_0(){
|
||||||
|
var superClassName = funNGenerator.getSuperClassName(0);
|
||||||
|
assertEquals("Fun0$$", superClassName);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void superClassName_1(){
|
||||||
|
var superClassName = funNGenerator.getSuperClassName(1);
|
||||||
|
assertEquals("Fun1$$", superClassName);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void specializedClassName_VoidVoid(){
|
||||||
|
var specializedClassName = funNGenerator.getSpecializedClassName(Arrays.asList(), voidType);
|
||||||
|
assertEquals("Fun0$$$_$Ljava$lang$Void$_$", specializedClassName);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void specializedClassName_VoidInt(){
|
||||||
|
var specializedClassName = funNGenerator.getSpecializedClassName(Arrays.asList(), integerType);
|
||||||
|
assertEquals("Fun0$$$_$Ljava$lang$Integer$_$", specializedClassName);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void specializedClassName_IntInt(){
|
||||||
|
var specializedClassName = funNGenerator.getSpecializedClassName(Arrays.asList(integerType), integerType);
|
||||||
|
assertEquals("Fun1$$$_$Ljava$lang$Integer$_$Ljava$lang$Integer$_$", specializedClassName);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void specializedClassName_IntT(){
|
||||||
|
var specializedClassName = funNGenerator.getSpecializedClassName(Arrays.asList(integerType), genericT);
|
||||||
|
assertEquals("Fun1$$$_$Ljava$lang$Integer$_$LT$_$", specializedClassName);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void specializedClassName_IntTPH(){
|
||||||
|
var specializedClassName = funNGenerator.getSpecializedClassName(Arrays.asList(integerType), TypePlaceholder.fresh(null));
|
||||||
|
assertEquals("Fun1$$$_$Ljava$lang$Integer$_$LTPH$_$", specializedClassName);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void signature_IntInt(){
|
||||||
|
var classSignature = funNGenerator.getSpecializedSignature(Arrays.asList(integerType), integerType);
|
||||||
|
assertEquals("LFun1$$$_$Ljava$lang$Integer$_$Ljava$lang$Integer$_$;", classSignature);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void signature_IntT(){
|
||||||
|
var classSignature = funNGenerator.getSpecializedSignature(Arrays.asList(integerType), genericT);
|
||||||
|
assertEquals("LFun1$$$_$Ljava$lang$Integer$_$LT$_$<TT;>;", classSignature);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void signature_TPHTPH(){
|
||||||
|
var classSignature = funNGenerator.getSpecializedSignature(Arrays.asList(tph), tph);
|
||||||
|
assertEquals(String.format("LFun1$$$_$LTPH$_$LTPH$_$<T%s$;T%s$;>;",tph.getName(), tph.getName()), classSignature);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void descriptor_IntInt(){
|
||||||
|
var classDescriptor = funNGenerator.getSpecializedDescriptor(Arrays.asList(integerType), integerType);
|
||||||
|
//does not have to contain L and ; because TypeToDescriptor returns the descriptor without these characters as well
|
||||||
|
assertEquals("Fun1$$$_$Ljava$lang$Integer$_$Ljava$lang$Integer$_$", classDescriptor);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void descriptor_IntT(){
|
||||||
|
var classDescriptor = funNGenerator.getSpecializedDescriptor(Arrays.asList(integerType), genericT);
|
||||||
|
//does not have to contain L and ; because TypeToDescriptor returns the descriptor without these characters as well
|
||||||
|
assertEquals("Fun1$$$_$Ljava$lang$Integer$_$LT$_$", classDescriptor);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void descriptor_TPHTPH(){
|
||||||
|
var classDescriptor = funNGenerator.getSpecializedDescriptor(Arrays.asList(tph), tph);
|
||||||
|
//does not have to contain L and ; because TypeToDescriptor returns the descriptor without these characters as well
|
||||||
|
assertEquals("Fun1$$$_$LTPH$_$LTPH$_$", classDescriptor);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getArguments_Empty(){
|
||||||
|
var arguments = funNGenerator.getArguments(Arrays.asList());
|
||||||
|
assertTrue(arguments.isEmpty());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getArguments_Int(){
|
||||||
|
var arguments = funNGenerator.getArguments(Arrays.asList(integerType));
|
||||||
|
assertTrue(arguments.isEmpty());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getArguments_IntT(){
|
||||||
|
var arguments = funNGenerator.getArguments(Arrays.asList(integerType, genericT));
|
||||||
|
assertTrue(arguments.size() == 1);
|
||||||
|
assertTrue(arguments.contains(integerType));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getArguments_IntTInt(){
|
||||||
|
var arguments = funNGenerator.getArguments(Arrays.asList(integerType, genericT, integerType));
|
||||||
|
assertTrue(arguments.size() == 2);
|
||||||
|
assertTrue(arguments.contains(integerType));
|
||||||
|
assertTrue(arguments.contains(genericT));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getReturnType_Empty(){
|
||||||
|
var returnType = funNGenerator.getReturnType(Arrays.asList());
|
||||||
|
assertNull(returnType);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getReturnType_Int(){
|
||||||
|
var returnType = funNGenerator.getReturnType(Arrays.asList(integerType));
|
||||||
|
assertEquals(integerType, returnType);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getReturnType_IntT(){
|
||||||
|
var returnType = funNGenerator.getReturnType(Arrays.asList(integerType, genericT));
|
||||||
|
assertEquals(genericT, returnType);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void superBytecode_0(){
|
||||||
|
var superBytecode = funNGenerator.generateSuperBytecode(0);
|
||||||
|
assertArrayEquals(superBytecodeReference_0(), superBytecode);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void superBytecode_1(){
|
||||||
|
var superBytecode = funNGenerator.generateSuperBytecode(1);
|
||||||
|
assertArrayEquals(superBytecodeReference_1(), superBytecode);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void superBytecode_2(){
|
||||||
|
var superBytecode = funNGenerator.generateSuperBytecode(2);
|
||||||
|
assertArrayEquals(superBytecodeReference_2(), superBytecode);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void specializedBytecode_VoidInt(){
|
||||||
|
var specializedBytecode = funNGenerator.generateSpecializedBytecode(Arrays.asList(), integerType);
|
||||||
|
assertArrayEquals(specializedBytecodeReference_VoidInt(), specializedBytecode);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void specializedBytecode_IntInt(){
|
||||||
|
var specializedBytecode = funNGenerator.generateSpecializedBytecode(Arrays.asList(integerType), integerType);
|
||||||
|
assertArrayEquals(specializedBytecodeReference_IntInt(), specializedBytecode);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void specializedBytecode_TIntInt(){
|
||||||
|
var specializedBytecode = funNGenerator.generateSpecializedBytecode(Arrays.asList(genericT, integerType), integerType);
|
||||||
|
assertArrayEquals(specializedBytecodeReference_TIntInt(), specializedBytecode);
|
||||||
|
}
|
||||||
|
|
||||||
|
//super bytecode reference methods
|
||||||
|
private static byte[] superBytecodeReference_0() {
|
||||||
|
var classWriter = new ClassWriter(0);
|
||||||
|
classWriter.visit(V1_8, ACC_PUBLIC | ACC_ABSTRACT | ACC_INTERFACE, "Fun0$$", "<R:Ljava/lang/Object;>Ljava/lang/Object;", "java/lang/Object", null);
|
||||||
|
var methodVisitor = classWriter.visitMethod(ACC_PUBLIC | ACC_ABSTRACT, "apply", "()Ljava/lang/Object;", "()TR;", null);
|
||||||
|
methodVisitor.visitEnd();
|
||||||
|
classWriter.visitEnd();
|
||||||
|
return classWriter.toByteArray();
|
||||||
|
}
|
||||||
|
|
||||||
|
private static byte[] superBytecodeReference_1() {
|
||||||
|
var classWriter = new ClassWriter(0);
|
||||||
|
classWriter.visit(V1_8, ACC_PUBLIC | ACC_ABSTRACT | ACC_INTERFACE, "Fun1$$", "<T1:Ljava/lang/Object;R:Ljava/lang/Object;>Ljava/lang/Object;", "java/lang/Object", null);
|
||||||
|
var methodVisitor = classWriter.visitMethod(ACC_PUBLIC | ACC_ABSTRACT, "apply", "(Ljava/lang/Object;)Ljava/lang/Object;", "(TT1;)TR;", null);
|
||||||
|
methodVisitor.visitEnd();
|
||||||
|
classWriter.visitEnd();
|
||||||
|
return classWriter.toByteArray();
|
||||||
|
}
|
||||||
|
|
||||||
|
private static byte[] superBytecodeReference_2() {
|
||||||
|
ClassWriter classWriter = new ClassWriter(0);
|
||||||
|
classWriter.visit(V1_8, ACC_PUBLIC | ACC_ABSTRACT | ACC_INTERFACE, "Fun2$$", "<T1:Ljava/lang/Object;T2:Ljava/lang/Object;R:Ljava/lang/Object;>Ljava/lang/Object;", "java/lang/Object", null);
|
||||||
|
var methodVisitor = classWriter.visitMethod(ACC_PUBLIC | ACC_ABSTRACT, "apply", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", "(TT1;TT2;)TR;", null);
|
||||||
|
methodVisitor.visitEnd();
|
||||||
|
classWriter.visitEnd();
|
||||||
|
return classWriter.toByteArray();
|
||||||
|
}
|
||||||
|
|
||||||
|
//specialized bytecode reference methods
|
||||||
|
private static byte[] specializedBytecodeReference_VoidInt() {
|
||||||
|
ClassWriter classWriter = new ClassWriter(0);
|
||||||
|
classWriter.visit(V1_8, ACC_PUBLIC | ACC_ABSTRACT | ACC_INTERFACE, "Fun0$$$_$Ljava$lang$Integer$_$", "Ljava/lang/Object;LFun0$$<Ljava/lang/Integer;>;", "java/lang/Object", new String[]{"Fun0$$"});
|
||||||
|
classWriter.visitEnd();
|
||||||
|
return classWriter.toByteArray();
|
||||||
|
}
|
||||||
|
|
||||||
|
private static byte[] specializedBytecodeReference_IntInt() {
|
||||||
|
ClassWriter classWriter = new ClassWriter(0);
|
||||||
|
classWriter.visit(V1_8, ACC_PUBLIC | ACC_ABSTRACT | ACC_INTERFACE, "Fun1$$$_$Ljava$lang$Integer$_$Ljava$lang$Integer$_$", "Ljava/lang/Object;LFun1$$<Ljava/lang/Integer;Ljava/lang/Integer;>;", "java/lang/Object", new String[]{"Fun1$$"});
|
||||||
|
classWriter.visitEnd();
|
||||||
|
return classWriter.toByteArray();
|
||||||
|
}
|
||||||
|
|
||||||
|
private static byte[] specializedBytecodeReference_TIntInt() {
|
||||||
|
ClassWriter classWriter = new ClassWriter(0);
|
||||||
|
classWriter.visit(V1_8, ACC_PUBLIC | ACC_ABSTRACT | ACC_INTERFACE, "Fun2$$$_$LT$_$Ljava$lang$Integer$_$Ljava$lang$Integer$_$", "<T:Ljava/lang/Object;>Ljava/lang/Object;LFun2$$<TT;Ljava/lang/Integer;Ljava/lang/Integer;>;", "java/lang/Object", new String[]{"Fun2$$"});
|
||||||
|
classWriter.visitEnd();
|
||||||
|
return classWriter.toByteArray();
|
||||||
|
}
|
||||||
|
}
|
@ -20,18 +20,17 @@ import org.junit.Test;
|
|||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
public class GeneralParserTest{
|
public class GeneralParserTest{
|
||||||
private static final String rootDirectory = System.getProperty("user.dir")+"/test/parser/";
|
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void run(){
|
public void run(){
|
||||||
|
|
||||||
|
|
||||||
List<String> filenames = new ArrayList<String>();
|
List<String> filenames = new ArrayList<String>();
|
||||||
|
|
||||||
|
filenames.add("javFiles/parser/NewTest.jav");
|
||||||
|
//filenames.add("CastTest.jav");
|
||||||
/*
|
/*
|
||||||
filenames.add("NewTest.jav");
|
|
||||||
filenames.add("FieldInitializationTest.jav");
|
filenames.add("FieldInitializationTest.jav");
|
||||||
filenames.add("ImportTest.jav");
|
filenames.add("ImportTest.jav");
|
||||||
filenames.add("CastTest.jav");
|
|
||||||
filenames.add("StatementsTest.jav");
|
filenames.add("StatementsTest.jav");
|
||||||
//filenames.add("Methods.jav");
|
//filenames.add("Methods.jav");
|
||||||
filenames.add("ImportTestGeneric.jav");
|
filenames.add("ImportTestGeneric.jav");
|
||||||
@ -40,11 +39,14 @@ public class GeneralParserTest{
|
|||||||
//filenames.add("GenericFieldVarTest.jav");
|
//filenames.add("GenericFieldVarTest.jav");
|
||||||
filenames.add("FieldVarTest.jav");
|
filenames.add("FieldVarTest.jav");
|
||||||
filenames.add("StructuralTypes.jav");
|
filenames.add("StructuralTypes.jav");
|
||||||
|
filenames.add("ExtendsTest.jav");
|
||||||
*/
|
*/
|
||||||
// filenames.add("ExtendsTest.jav");
|
|
||||||
filenames.add("PackageNameTest.jav");
|
//filenames.add("PackageNameTest.jav");
|
||||||
try{
|
try{
|
||||||
new JavaTXCompiler(filenames.stream().map(s -> new File(rootDirectory + s)).collect(Collectors.toList()));
|
for(String filename : filenames){
|
||||||
|
new JavaTXCompiler(new File(Thread.currentThread().getContextClassLoader().getResource(filename).getPath()));
|
||||||
|
}
|
||||||
}catch(Exception exc){
|
}catch(Exception exc){
|
||||||
exc.printStackTrace();
|
exc.printStackTrace();
|
||||||
fail();
|
fail();
|
||||||
|
@ -6,8 +6,7 @@ import java.lang.Boolean;
|
|||||||
|
|
||||||
public class OLFun {
|
public class OLFun {
|
||||||
|
|
||||||
//f = x -> {return x + x;};
|
|
||||||
m(f, x) {
|
m(f, x) {
|
||||||
x = f.apply(x+x);
|
var y = f.apply(x + x) + 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -6,8 +6,9 @@ import java.lang.Boolean;
|
|||||||
|
|
||||||
public class OLFun2 {
|
public class OLFun2 {
|
||||||
|
|
||||||
x;
|
|
||||||
m(f){
|
m(f){
|
||||||
x = f.apply(x + x)
|
var x = 1;
|
||||||
|
var y = f.apply(x + x) + 1;
|
||||||
|
return y;
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -1,3 +1,4 @@
|
|||||||
|
|
||||||
class Test{
|
class Test{
|
||||||
method(){
|
method(){
|
||||||
if(true)i++;
|
if(true)i++;
|
10
src/test/resources/testBytecode/manually/OLFunTest.java
Normal file
10
src/test/resources/testBytecode/manually/OLFunTest.java
Normal file
@ -0,0 +1,10 @@
|
|||||||
|
public class OLFunTest{
|
||||||
|
public static void main(String[] args){
|
||||||
|
var olFun2 = new OLFun2();
|
||||||
|
Integer i = olFun2.m((Integer x) -> x);
|
||||||
|
i = olFun2.m((Double x) -> x.intValue());
|
||||||
|
|
||||||
|
Double d = olFun2.m((Integer x) -> Double.valueOf(x));
|
||||||
|
d = olFun2.m((Double x) -> x);
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user