forked from JavaTX/JavaCompilerCore
erzeugt bytecode fuer lambda
This commit is contained in:
parent
e702f745c3
commit
a8274bdc69
@ -1,7 +1,5 @@
|
|||||||
package de.dhbwstuttgart.bytecode;
|
package de.dhbwstuttgart.bytecode;
|
||||||
|
|
||||||
import java.awt.List;
|
|
||||||
import java.util.ArrayList;
|
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.Iterator;
|
import java.util.Iterator;
|
||||||
|
|
||||||
@ -20,6 +18,7 @@ import de.dhbwstuttgart.syntaxtree.type.GenericRefType;
|
|||||||
import de.dhbwstuttgart.syntaxtree.type.RefType;
|
import de.dhbwstuttgart.syntaxtree.type.RefType;
|
||||||
import de.dhbwstuttgart.syntaxtree.type.SuperWildcardType;
|
import de.dhbwstuttgart.syntaxtree.type.SuperWildcardType;
|
||||||
import de.dhbwstuttgart.syntaxtree.type.TypePlaceholder;
|
import de.dhbwstuttgart.syntaxtree.type.TypePlaceholder;
|
||||||
|
import de.dhbwstuttgart.typeinference.result.ResultSet;
|
||||||
|
|
||||||
public class BytecodeGen implements ASTVisitor {
|
public class BytecodeGen implements ASTVisitor {
|
||||||
|
|
||||||
@ -30,15 +29,17 @@ public class BytecodeGen implements ASTVisitor {
|
|||||||
|
|
||||||
String className;
|
String className;
|
||||||
private boolean isInterface;
|
private boolean isInterface;
|
||||||
|
private ResultSet resultSet;
|
||||||
|
private int indexOfFirstParam = 0;
|
||||||
|
|
||||||
// stores parameter, local vars and the next index on the local variable table, which use for aload_i, astore_i,...
|
// stores parameter, local vars and the next index on the local variable table, which use for aload_i, astore_i,...
|
||||||
HashMap<String, Integer> paramsAndLocals;// = new HashMap<>();
|
HashMap<String, Integer> paramsAndLocals = new HashMap<>();
|
||||||
byte[] bytecode;
|
byte[] bytecode;
|
||||||
HashMap<String,byte[]> classFiles;
|
HashMap<String,byte[]> classFiles;
|
||||||
|
|
||||||
public BytecodeGen(HashMap<String,byte[]> classFiles) {
|
public BytecodeGen(HashMap<String,byte[]> classFiles, ResultSet resultSet) {
|
||||||
this.classFiles = classFiles;
|
this.classFiles = classFiles;
|
||||||
paramsAndLocals = new HashMap<>();
|
this.resultSet = resultSet;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -46,7 +47,7 @@ public class BytecodeGen implements ASTVisitor {
|
|||||||
for(ClassOrInterface cl : sourceFile.getClasses()) {
|
for(ClassOrInterface cl : sourceFile.getClasses()) {
|
||||||
isInterface = (cl.getModifiers()&512)==512;
|
isInterface = (cl.getModifiers()&512)==512;
|
||||||
System.out.println("IS Interface = "+"modifiers= "+cl.getModifiers()+" ->"+(cl.getModifiers()&512) + isInterface);
|
System.out.println("IS Interface = "+"modifiers= "+cl.getModifiers()+" ->"+(cl.getModifiers()&512) + isInterface);
|
||||||
BytecodeGen classGen = new BytecodeGen(classFiles);
|
BytecodeGen classGen = new BytecodeGen(classFiles, resultSet);
|
||||||
cl.accept(classGen);
|
cl.accept(classGen);
|
||||||
classGen.writeClass(cl.getClassName().toString());
|
classGen.writeClass(cl.getClassName().toString());
|
||||||
}
|
}
|
||||||
@ -87,32 +88,35 @@ public class BytecodeGen implements ASTVisitor {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void visit(Constructor field) {
|
public void visit(Constructor field) {
|
||||||
Descriptor desc = new Descriptor(field);
|
Descriptor desc = new Descriptor(field, resultSet);
|
||||||
MethodVisitor mv = cw.visitMethod(Opcodes.ACC_PUBLIC, "<init>", desc.getDesc(), null, null);
|
MethodVisitor mv = cw.visitMethod(Opcodes.ACC_PUBLIC, "<init>", desc.getDesc(), null, null);
|
||||||
mv.visitCode();
|
mv.visitCode();
|
||||||
System.out.println("-----Constructor-----");
|
System.out.println("-----Constructor-----");
|
||||||
BytecodeGenMethod gen = new BytecodeGenMethod(className,field, mv,paramsAndLocals,desc.getDesc(),cw,isInterface);
|
BytecodeGenMethod gen = new BytecodeGenMethod(className,resultSet,field, mv,paramsAndLocals,desc.getDesc(),cw,isInterface);
|
||||||
|
|
||||||
// mv.visitInsn(Opcodes.RETURN);
|
mv.visitInsn(Opcodes.RETURN);
|
||||||
mv.visitMaxs(0, 0);
|
mv.visitMaxs(0, 0);
|
||||||
mv.visitEnd();
|
mv.visitEnd();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void visit(Method method) {
|
public void visit(Method method) {
|
||||||
|
// TODO: check if the method is static => if static then the first param will be stored in pos 0
|
||||||
|
// else it will be stored in pos 1 and this will be stored in pos 0
|
||||||
method.getParameterList().accept(this);
|
method.getParameterList().accept(this);
|
||||||
Descriptor methDesc = new Descriptor(method);
|
Descriptor methDesc = new Descriptor(method,resultSet);
|
||||||
System.out.println("-----Method-----");
|
System.out.println("-----Method-----");
|
||||||
MethodVisitor mv = cw.visitMethod(Opcodes.ACC_PUBLIC, method.getName(), methDesc.getDesc(), null, null);
|
MethodVisitor mv = cw.visitMethod(Opcodes.ACC_PUBLIC, method.getName(), methDesc.getDesc(), null, null);
|
||||||
mv.visitCode();
|
mv.visitCode();
|
||||||
|
|
||||||
BytecodeGenMethod gen = new BytecodeGenMethod(className,method, mv,paramsAndLocals,methDesc.getDesc(),cw,isInterface);
|
BytecodeGenMethod gen = new BytecodeGenMethod(className,resultSet,method, mv,paramsAndLocals,methDesc.getDesc(),cw,isInterface);
|
||||||
mv.visitMaxs(0, 0);
|
mv.visitMaxs(0, 0);
|
||||||
mv.visitEnd();
|
mv.visitEnd();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void visit(ParameterList formalParameters) {
|
public void visit(ParameterList formalParameters) {
|
||||||
|
paramsAndLocals = new HashMap<>();
|
||||||
Iterator<FormalParameter> itr = formalParameters.iterator();
|
Iterator<FormalParameter> itr = formalParameters.iterator();
|
||||||
int i = 1;
|
int i = 1;
|
||||||
while(itr.hasNext()) {
|
while(itr.hasNext()) {
|
||||||
|
@ -6,6 +6,7 @@ import java.lang.invoke.MethodHandles;
|
|||||||
import java.lang.invoke.MethodType;
|
import java.lang.invoke.MethodType;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
|
import java.util.Iterator;
|
||||||
|
|
||||||
import de.dhbwstuttgart.syntaxtree.statement.*;
|
import de.dhbwstuttgart.syntaxtree.statement.*;
|
||||||
import org.objectweb.asm.ClassWriter;
|
import org.objectweb.asm.ClassWriter;
|
||||||
@ -15,11 +16,13 @@ import org.objectweb.asm.Opcodes;
|
|||||||
import org.objectweb.asm.Type;
|
import org.objectweb.asm.Type;
|
||||||
|
|
||||||
import de.dhbwstuttgart.parser.SyntaxTreeGenerator.AssignToLocal;
|
import de.dhbwstuttgart.parser.SyntaxTreeGenerator.AssignToLocal;
|
||||||
|
import de.dhbwstuttgart.syntaxtree.FormalParameter;
|
||||||
import de.dhbwstuttgart.syntaxtree.Method;
|
import de.dhbwstuttgart.syntaxtree.Method;
|
||||||
import de.dhbwstuttgart.syntaxtree.StatementVisitor;
|
import de.dhbwstuttgart.syntaxtree.StatementVisitor;
|
||||||
import de.dhbwstuttgart.syntaxtree.statement.literal.Literal;
|
import de.dhbwstuttgart.syntaxtree.statement.literal.Literal;
|
||||||
import de.dhbwstuttgart.syntaxtree.statement.literal.Null;
|
import de.dhbwstuttgart.syntaxtree.statement.literal.Null;
|
||||||
import de.dhbwstuttgart.syntaxtree.type.RefTypeOrTPHOrWildcardOrGeneric;
|
import de.dhbwstuttgart.syntaxtree.type.RefTypeOrTPHOrWildcardOrGeneric;
|
||||||
|
import de.dhbwstuttgart.typeinference.result.ResultSet;
|
||||||
|
|
||||||
public class BytecodeGenMethod implements StatementVisitor{
|
public class BytecodeGenMethod implements StatementVisitor{
|
||||||
|
|
||||||
@ -30,6 +33,7 @@ public class BytecodeGenMethod implements StatementVisitor{
|
|||||||
private String className;
|
private String className;
|
||||||
private int lamCounter;
|
private int lamCounter;
|
||||||
private ClassWriter cw;
|
private ClassWriter cw;
|
||||||
|
private ResultSet resultSet;
|
||||||
private boolean isInterface;
|
private boolean isInterface;
|
||||||
|
|
||||||
//for tests **
|
//for tests **
|
||||||
@ -37,16 +41,18 @@ public class BytecodeGenMethod implements StatementVisitor{
|
|||||||
private String fieldDesc;
|
private String fieldDesc;
|
||||||
private Expression rightSideTemp;
|
private Expression rightSideTemp;
|
||||||
private String where;
|
private String where;
|
||||||
private boolean isRightSideALambda = false;
|
private boolean isRightSideALambda = false;
|
||||||
|
private KindOfLambda kindOfLambda;
|
||||||
|
|
||||||
private ArrayList<RefTypeOrTPHOrWildcardOrGeneric> varsFunInterface;
|
private ArrayList<RefTypeOrTPHOrWildcardOrGeneric> varsFunInterface;
|
||||||
|
|
||||||
public BytecodeGenMethod(String className, Method m, MethodVisitor mv, HashMap<String, Integer> paramsAndLocals,
|
public BytecodeGenMethod(String className,ResultSet resultSet, Method m, MethodVisitor mv, HashMap<String, Integer> paramsAndLocals,
|
||||||
String desc, ClassWriter cw, boolean isInterface) {
|
String desc, ClassWriter cw, boolean isInterface) {
|
||||||
|
|
||||||
this.where = "<<<<<< NORMAL METHOD >>>>>>";
|
this.where = "<<<<<< NORMAL METHOD >>>>>>";
|
||||||
|
|
||||||
this.className = className;
|
this.className = className;
|
||||||
|
this.resultSet = resultSet;
|
||||||
this.m = m;
|
this.m = m;
|
||||||
this.mv = mv;
|
this.mv = mv;
|
||||||
this.paramsAndLocals = paramsAndLocals;
|
this.paramsAndLocals = paramsAndLocals;
|
||||||
@ -56,27 +62,42 @@ public class BytecodeGenMethod implements StatementVisitor{
|
|||||||
this.lamCounter = -1;
|
this.lamCounter = -1;
|
||||||
|
|
||||||
this.varsFunInterface = new ArrayList<>();
|
this.varsFunInterface = new ArrayList<>();
|
||||||
|
System.out.println("PARAMS = "+this.paramsAndLocals.size());
|
||||||
this.m.block.accept(this);
|
this.m.block.accept(this);
|
||||||
|
System.out.println("PARAMS = "+this.paramsAndLocals.size());
|
||||||
|
for(int i = 0; i<this.paramsAndLocals.size();i++) {
|
||||||
|
System.out.println(this.paramsAndLocals.keySet().toArray()[i]);
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public BytecodeGenMethod(LambdaExpression lambdaExpression, MethodVisitor mv,
|
public BytecodeGenMethod(LambdaExpression lambdaExpression,ResultSet resultSet ,MethodVisitor mv,
|
||||||
HashMap<String, Integer> paramsAndLocals, String desc,boolean isInterface) {
|
String desc,int indexOfFirstParamLam, boolean isInterface) {
|
||||||
System.out.println("\t\t++++++IN LAMBDA -------");
|
System.out.println("\t\t++++++IN LAMBDA -------");
|
||||||
|
|
||||||
this.where = "<<<<<< LAMBDA METHOD >>>>>>";
|
this.where = "<<<<<< LAMBDA METHOD >>>>>>";
|
||||||
|
this.resultSet = resultSet;
|
||||||
this.mv = mv;
|
this.mv = mv;
|
||||||
this.paramsAndLocals = paramsAndLocals;
|
|
||||||
this.desc = desc;
|
this.desc = desc;
|
||||||
this.isInterface = isInterface;
|
this.isInterface = isInterface;
|
||||||
this.lamCounter = -1;
|
this.lamCounter = -1;
|
||||||
this.varsFunInterface = new ArrayList<>();
|
this.varsFunInterface = new ArrayList<>();
|
||||||
|
|
||||||
|
Iterator<FormalParameter> itr = lambdaExpression.params.iterator();
|
||||||
|
int i = indexOfFirstParamLam;
|
||||||
|
while(itr.hasNext()) {
|
||||||
|
FormalParameter fp = itr.next();
|
||||||
|
this.paramsAndLocals.put(fp.getName(), i);
|
||||||
|
i++;
|
||||||
|
}
|
||||||
lambdaExpression.methodBody.accept(this);
|
lambdaExpression.methodBody.accept(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private String getResolvedType(RefTypeOrTPHOrWildcardOrGeneric type) {
|
||||||
|
return resultSet.resolveType(type).resolvedType.toString().replace(".", "/");
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void visit(Block block) {
|
public void visit(Block block) {
|
||||||
for(Statement stmt : block.getStatements()) {
|
for(Statement stmt : block.getStatements()) {
|
||||||
@ -98,7 +119,7 @@ public class BytecodeGenMethod implements StatementVisitor{
|
|||||||
// ??
|
// ??
|
||||||
@Override
|
@Override
|
||||||
public void visit(LocalVar localVar) {
|
public void visit(LocalVar localVar) {
|
||||||
System.out.println("in Local Var");
|
System.out.println("in Local Var: " + localVar.name);
|
||||||
mv.visitVarInsn(Opcodes.ALOAD, paramsAndLocals.get(localVar.name));
|
mv.visitVarInsn(Opcodes.ALOAD, paramsAndLocals.get(localVar.name));
|
||||||
}
|
}
|
||||||
// ??
|
// ??
|
||||||
@ -106,7 +127,7 @@ public class BytecodeGenMethod implements StatementVisitor{
|
|||||||
public void visit(LocalVarDecl localVarDecl) {
|
public void visit(LocalVarDecl localVarDecl) {
|
||||||
// Integer i;
|
// Integer i;
|
||||||
// paramsAndLocals.put(localVarDecl.getName(), paramsAndLocals.size()+1);
|
// paramsAndLocals.put(localVarDecl.getName(), paramsAndLocals.size()+1);
|
||||||
System.out.println("In localVarDecl");
|
System.out.println("In localVarDecl :: "+localVarDecl.getName());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -143,28 +164,49 @@ public class BytecodeGenMethod implements StatementVisitor{
|
|||||||
public void visit(LambdaExpression lambdaExpression) {
|
public void visit(LambdaExpression lambdaExpression) {
|
||||||
System.out.println("\n++ In Lambda: ");
|
System.out.println("\n++ In Lambda: ");
|
||||||
this.lamCounter++;
|
this.lamCounter++;
|
||||||
|
Descriptor lamDesc = new Descriptor(lambdaExpression, resultSet);
|
||||||
//Call site, which, when invoked, returns an instance of the functional interface to which
|
//Call site, which, when invoked, returns an instance of the functional interface to which
|
||||||
//the lambda is being converted
|
//the lambda is being converted
|
||||||
MethodType mt = MethodType.methodType(CallSite.class, MethodHandles.Lookup.class, String.class,
|
MethodType mt = MethodType.methodType(CallSite.class, MethodHandles.Lookup.class, String.class,
|
||||||
MethodType.class, MethodType.class, MethodHandle.class, MethodType.class);
|
MethodType.class, MethodType.class, MethodHandle.class, MethodType.class);
|
||||||
|
|
||||||
|
|
||||||
Handle bootstrap = new Handle(Opcodes.H_INVOKESTATIC, "java/lang/invoke/LambdaMetafactory",
|
Handle bootstrap = new Handle(Opcodes.H_INVOKESTATIC, "java/lang/invoke/LambdaMetafactory",
|
||||||
"metafactory", mt.toMethodDescriptorString(), false);
|
"metafactory", mt.toMethodDescriptorString(), false);
|
||||||
String methodName = "lambda$new$" + this.lamCounter;
|
String methodName = "lambda$new$" + this.lamCounter;
|
||||||
// Type erasure
|
// Type erasure
|
||||||
Type arg1 = Type.getMethodType("()V");
|
Type arg1 = Type.getMethodType(lamDesc.getDesc());
|
||||||
// real Type
|
// real Type
|
||||||
Type arg3 = Type.getMethodType("()V");
|
Type arg3 = Type.getMethodType(lamDesc.getDesc());
|
||||||
Handle arg2 = new Handle(Opcodes.H_INVOKESTATIC, this.className, methodName,
|
|
||||||
|
int staticOrSpecial=0;
|
||||||
|
int staticOrInstance=0;
|
||||||
|
int indexOfFirstParamLam = 0;
|
||||||
|
this.kindOfLambda = new KindOfLambda(lambdaExpression);
|
||||||
|
|
||||||
|
if(kindOfLambda.isInstanceCapturingLambda()) {
|
||||||
|
mv.visitVarInsn(Opcodes.ALOAD, 0);
|
||||||
|
staticOrSpecial = Opcodes.H_INVOKESPECIAL;
|
||||||
|
indexOfFirstParamLam = 1;
|
||||||
|
}else {
|
||||||
|
staticOrSpecial = Opcodes.H_INVOKESTATIC;
|
||||||
|
staticOrInstance = Opcodes.ACC_STATIC;
|
||||||
|
}
|
||||||
|
|
||||||
|
// first check if capturing lambda then invokestatic or invokespecial
|
||||||
|
Handle arg2 = new Handle(staticOrSpecial, this.className, methodName,
|
||||||
arg3.toString(),false);
|
arg3.toString(),false);
|
||||||
mv.visitInvokeDynamicInsn("run", "()Ljava/lang/Runnable;", bootstrap,
|
// Descriptor of functional interface methode
|
||||||
|
Descriptor fiMethodDesc = new Descriptor(kindOfLambda.getArgumentList(), lambdaExpression.getType(),resultSet);
|
||||||
|
|
||||||
|
// Desc: (this/nothing)TargetType
|
||||||
|
mv.visitInvokeDynamicInsn("apply", fiMethodDesc.getDesc(), bootstrap,
|
||||||
arg1, arg2,arg3);
|
arg1, arg2,arg3);
|
||||||
|
|
||||||
MethodVisitor mvLambdaBody = cw.visitMethod(Opcodes.ACC_PRIVATE+ Opcodes.ACC_STATIC + Opcodes.ACC_SYNTHETIC,
|
MethodVisitor mvLambdaBody = cw.visitMethod(Opcodes.ACC_PRIVATE+ staticOrInstance + Opcodes.ACC_SYNTHETIC,
|
||||||
methodName, arg3.toString(), null, null);
|
methodName, arg3.toString(), null, null);
|
||||||
// new BytecodeGenLambda(lambdaExpression, mvLambdaBody);
|
|
||||||
HashMap<String, Integer> paramsAndLocalsLambda = new HashMap<>();
|
new BytecodeGenMethod(lambdaExpression,this.resultSet,mvLambdaBody,arg3.toString(),indexOfFirstParamLam,isInterface);
|
||||||
new BytecodeGenMethod(lambdaExpression, mvLambdaBody, paramsAndLocalsLambda, arg3.toString(),isInterface);
|
|
||||||
|
|
||||||
mvLambdaBody.visitMaxs(0, 0);
|
mvLambdaBody.visitMaxs(0, 0);
|
||||||
mvLambdaBody.visitEnd();
|
mvLambdaBody.visitEnd();
|
||||||
@ -189,12 +231,13 @@ public class BytecodeGenMethod implements StatementVisitor{
|
|||||||
System.out.println("in fieldVar " + fieldVar.fieldVarName + " ** receiver: "+fieldVar.receiver);
|
System.out.println("in fieldVar " + fieldVar.fieldVarName + " ** receiver: "+fieldVar.receiver);
|
||||||
|
|
||||||
fieldName = fieldVar.fieldVarName;
|
fieldName = fieldVar.fieldVarName;
|
||||||
fieldDesc = fieldVar.getType().toString();
|
fieldDesc = "L"+getResolvedType(fieldVar.getType())+";";
|
||||||
|
|
||||||
fieldVar.receiver.accept(this);
|
fieldVar.receiver.accept(this);
|
||||||
// test (if)
|
// test (if)
|
||||||
if(!fieldVar.receiver.getClass().equals(StaticClassName.class)) {
|
if(!fieldVar.receiver.getClass().equals(StaticClassName.class)) {
|
||||||
mv.visitFieldInsn(Opcodes.GETFIELD,fieldVar.getType().toString(),fieldName ,fieldDesc);
|
mv.visitFieldInsn(Opcodes.GETFIELD,getResolvedType(fieldVar.receiver.getType()),
|
||||||
|
fieldName ,fieldDesc);
|
||||||
}
|
}
|
||||||
|
|
||||||
// mv.visitFieldInsn(Opcodes.GETSTATIC, fieldVar.receiver.getType().toString().replace(".", "/"),
|
// mv.visitFieldInsn(Opcodes.GETSTATIC, fieldVar.receiver.getType().toString().replace(".", "/"),
|
||||||
@ -231,16 +274,16 @@ public class BytecodeGenMethod implements StatementVisitor{
|
|||||||
methodCall.receiver.accept(this);
|
methodCall.receiver.accept(this);
|
||||||
methodCall.arglist.accept(this);
|
methodCall.arglist.accept(this);
|
||||||
|
|
||||||
Descriptor mDesc = new Descriptor(methodCall.arglist, methodCall.getType());
|
Descriptor mDesc = new Descriptor(methodCall.arglist, methodCall.getType(),resultSet);
|
||||||
|
|
||||||
System.out.println("is Vars empty: "+varsFunInterface.isEmpty());
|
System.out.println("is Vars empty: "+varsFunInterface.isEmpty());
|
||||||
|
|
||||||
// is methodCall.receiver functional Interface)?
|
// is methodCall.receiver functional Interface)?
|
||||||
if(varsFunInterface.contains(methodCall.receiver.getType())) {
|
if(varsFunInterface.contains(methodCall.receiver.getType())) {
|
||||||
mv.visitMethodInsn(Opcodes.INVOKEINTERFACE, methodCall.receiver.getType().toString().replace(".", "/"),
|
mv.visitMethodInsn(Opcodes.INVOKEINTERFACE, getResolvedType(methodCall.receiver.getType()),
|
||||||
methodCall.name, mDesc.getDesc(), false);
|
methodCall.name, mDesc.getDesc(), false);
|
||||||
}else {
|
}else {
|
||||||
mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, methodCall.receiver.getType().toString().replace(".", "/"),
|
mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, getResolvedType(methodCall.receiver.getType()),
|
||||||
methodCall.name, mDesc.getDesc(), isInterface);
|
methodCall.name, mDesc.getDesc(), isInterface);
|
||||||
}
|
}
|
||||||
// test
|
// test
|
||||||
@ -282,6 +325,7 @@ public class BytecodeGenMethod implements StatementVisitor{
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void visit(Return aReturn) {
|
public void visit(Return aReturn) {
|
||||||
|
aReturn.retexpr.accept(this);
|
||||||
mv.visitInsn(Opcodes.ARETURN);
|
mv.visitInsn(Opcodes.ARETURN);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -340,9 +384,11 @@ public class BytecodeGenMethod implements StatementVisitor{
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void visit(ArgumentList argumentList) {
|
public void visit(ArgumentList argumentList) {
|
||||||
|
System.out.println("in ArgumentList: ");
|
||||||
for(Expression al : argumentList.getArguments()) {
|
for(Expression al : argumentList.getArguments()) {
|
||||||
al.accept(this);
|
al.accept(this);
|
||||||
}
|
}
|
||||||
|
System.out.println("out from Argumentlist");
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -364,6 +410,8 @@ public class BytecodeGenMethod implements StatementVisitor{
|
|||||||
varsFunInterface.add(assignLeftSide.localVar.getType());
|
varsFunInterface.add(assignLeftSide.localVar.getType());
|
||||||
paramsAndLocals.put(assignLeftSide.localVar.name, paramsAndLocals.size()+1);
|
paramsAndLocals.put(assignLeftSide.localVar.name, paramsAndLocals.size()+1);
|
||||||
mv.visitVarInsn(Opcodes.ASTORE, paramsAndLocals.size());
|
mv.visitVarInsn(Opcodes.ASTORE, paramsAndLocals.size());
|
||||||
|
// Debug:::
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
package de.dhbwstuttgart.bytecode;
|
package de.dhbwstuttgart.bytecode;
|
||||||
|
|
||||||
import java.awt.List;
|
import java.util.List;
|
||||||
import java.util.Iterator;
|
import java.util.Iterator;
|
||||||
|
|
||||||
import de.dhbwstuttgart.syntaxtree.Constructor;
|
import de.dhbwstuttgart.syntaxtree.Constructor;
|
||||||
@ -8,45 +8,74 @@ import de.dhbwstuttgart.syntaxtree.FormalParameter;
|
|||||||
import de.dhbwstuttgart.syntaxtree.Method;
|
import de.dhbwstuttgart.syntaxtree.Method;
|
||||||
import de.dhbwstuttgart.syntaxtree.statement.ArgumentList;
|
import de.dhbwstuttgart.syntaxtree.statement.ArgumentList;
|
||||||
import de.dhbwstuttgart.syntaxtree.statement.Expression;
|
import de.dhbwstuttgart.syntaxtree.statement.Expression;
|
||||||
|
import de.dhbwstuttgart.syntaxtree.statement.LambdaExpression;
|
||||||
import de.dhbwstuttgart.syntaxtree.type.RefTypeOrTPHOrWildcardOrGeneric;
|
import de.dhbwstuttgart.syntaxtree.type.RefTypeOrTPHOrWildcardOrGeneric;
|
||||||
|
import de.dhbwstuttgart.typeinference.result.ResultSet;
|
||||||
|
|
||||||
public class Descriptor {
|
public class Descriptor {
|
||||||
String desc;
|
String desc;
|
||||||
|
|
||||||
public Descriptor(Method method) {
|
public Descriptor(Method method, ResultSet resultSet) {
|
||||||
desc = "(";
|
desc = "(";
|
||||||
Iterator<FormalParameter> itr = method.getParameterList().iterator();
|
Iterator<FormalParameter> itr = method.getParameterList().iterator();
|
||||||
while(itr.hasNext()) {
|
while(itr.hasNext()) {
|
||||||
FormalParameter fp = itr.next();
|
FormalParameter fp = itr.next();
|
||||||
desc = desc + "L"+fp.getType().toString().replace(".", "/") + ";";
|
desc = desc + "L"+resultSet.resolveType(fp.getType()).resolvedType.toString().replace(".", "/") + ";";
|
||||||
}
|
|
||||||
if(method.getReturnType().toString().equals("void")){
|
|
||||||
desc = desc + ")V";
|
|
||||||
}else {
|
|
||||||
desc = desc + ")" + "L"+method.getReturnType().toString().replace(".", "/")+";";
|
|
||||||
}
|
}
|
||||||
|
desc = addReturnType(desc,method.getReturnType(), resultSet);
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public Descriptor(Constructor constructor) {
|
private String addReturnType(String desc2, RefTypeOrTPHOrWildcardOrGeneric returnType, ResultSet resultSet) {
|
||||||
|
System.out.println("DescType = "+returnType.toString());
|
||||||
|
if(resultSet.resolveType(returnType).resolvedType.toString().equals("void")){
|
||||||
|
desc = desc + ")V";
|
||||||
|
}else {
|
||||||
|
desc = desc + ")" + "L"+resultSet.resolveType(returnType).resolvedType.toString().replace(".", "/")+";";
|
||||||
|
}
|
||||||
|
return desc;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Descriptor(Constructor constructor, ResultSet resultSet) {
|
||||||
desc = "(";
|
desc = "(";
|
||||||
Iterator<FormalParameter> itr = constructor.getParameterList().iterator();
|
Iterator<FormalParameter> itr = constructor.getParameterList().iterator();
|
||||||
while(itr.hasNext()) {
|
while(itr.hasNext()) {
|
||||||
FormalParameter fp = itr.next();
|
FormalParameter fp = itr.next();
|
||||||
desc = desc + "L"+fp.getType().toString().replace(".", "/") + ";";
|
desc = desc + "L"+resultSet.resolveType(fp.getType()).resolvedType.toString().replace(".", "/") + ";";
|
||||||
}
|
}
|
||||||
desc = desc + ")V";
|
desc = desc + ")V";
|
||||||
}
|
}
|
||||||
|
|
||||||
public Descriptor(ArgumentList argList, RefTypeOrTPHOrWildcardOrGeneric returnType) {
|
public Descriptor(LambdaExpression lambdaExpr, ResultSet resultSet) {
|
||||||
|
desc = "(";
|
||||||
|
Iterator<FormalParameter> itr = lambdaExpr.params.iterator();
|
||||||
|
while(itr.hasNext()) {
|
||||||
|
FormalParameter fp = itr.next();
|
||||||
|
desc = desc + "L"+resultSet.resolveType(fp.getType()).resolvedType.toString().replace(".", "/") + ";";
|
||||||
|
}
|
||||||
|
desc = addReturnType(desc, lambdaExpr.getReturnType(), resultSet);
|
||||||
|
}
|
||||||
|
|
||||||
|
public Descriptor(ArgumentList argList, RefTypeOrTPHOrWildcardOrGeneric returnType, ResultSet resultSet) {
|
||||||
desc = "(";
|
desc = "(";
|
||||||
for(Expression e : argList.getArguments()) {
|
for(Expression e : argList.getArguments()) {
|
||||||
desc = desc + "L"+e.getType().toString().replace(".", "/") + ";";
|
desc = desc + "L"+resultSet.resolveType(e.getType()).resolvedType.toString().replace(".", "/") + ";";
|
||||||
}
|
}
|
||||||
desc = desc + ")"+returnType.toString();
|
desc = addReturnType(desc, returnType, resultSet);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Descriptor(List<RefTypeOrTPHOrWildcardOrGeneric> argumentList,RefTypeOrTPHOrWildcardOrGeneric returnType ,ResultSet resultSet) {
|
||||||
|
desc = "(";
|
||||||
|
Iterator<RefTypeOrTPHOrWildcardOrGeneric> itr = argumentList.iterator();
|
||||||
|
while(itr.hasNext()) {
|
||||||
|
RefTypeOrTPHOrWildcardOrGeneric rt = itr.next();
|
||||||
|
desc = desc + "L"+resultSet.resolveType(rt).resolvedType.toString().replace(".", "/")+";";
|
||||||
|
}
|
||||||
|
desc = desc + ")"+"L"+resultSet.resolveType(returnType).resolvedType.toString().replace(".", "/")+";";
|
||||||
|
}
|
||||||
|
|
||||||
public String getDesc() {
|
public String getDesc() {
|
||||||
return this.desc;
|
return this.desc;
|
||||||
}
|
}
|
||||||
|
@ -1,24 +1,33 @@
|
|||||||
package de.dhbwstuttgart.bytecode;
|
package de.dhbwstuttgart.bytecode;
|
||||||
|
|
||||||
import de.dhbwstuttgart.syntaxtree.statement.*;
|
import de.dhbwstuttgart.syntaxtree.statement.*;
|
||||||
import org.objectweb.asm.MethodVisitor;
|
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
import de.dhbwstuttgart.parser.SyntaxTreeGenerator.AssignToLocal;
|
import de.dhbwstuttgart.parser.SyntaxTreeGenerator.AssignToLocal;
|
||||||
import de.dhbwstuttgart.syntaxtree.StatementVisitor;
|
import de.dhbwstuttgart.syntaxtree.StatementVisitor;
|
||||||
import de.dhbwstuttgart.syntaxtree.statement.literal.Literal;
|
import de.dhbwstuttgart.syntaxtree.statement.literal.Literal;
|
||||||
import de.dhbwstuttgart.syntaxtree.statement.literal.Null;
|
import de.dhbwstuttgart.syntaxtree.statement.literal.Null;
|
||||||
|
import de.dhbwstuttgart.syntaxtree.type.RefTypeOrTPHOrWildcardOrGeneric;
|
||||||
|
|
||||||
public class BytecodeGenLambda implements StatementVisitor{
|
public class KindOfLambda implements StatementVisitor{
|
||||||
private LambdaExpression lambdaExpression;
|
private boolean isInstanceCapturingLambda = false;
|
||||||
private MethodVisitor mv;
|
private List<RefTypeOrTPHOrWildcardOrGeneric> argumentList = new ArrayList<>();
|
||||||
|
|
||||||
public BytecodeGenLambda(LambdaExpression lambdaExpression, MethodVisitor mv) {
|
public KindOfLambda(LambdaExpression lambdaExpression) {
|
||||||
this.lambdaExpression = lambdaExpression;
|
lambdaExpression.methodBody.accept(this);
|
||||||
this.mv = mv;
|
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public boolean isInstanceCapturingLambda() {
|
||||||
|
return this.isInstanceCapturingLambda;
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<RefTypeOrTPHOrWildcardOrGeneric> getArgumentList() {
|
||||||
|
return argumentList;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void visit(ArgumentList argumentList) {
|
public void visit(ArgumentList argumentList) {
|
||||||
// TODO Auto-generated method stub
|
// TODO Auto-generated method stub
|
||||||
@ -27,14 +36,12 @@ public class BytecodeGenLambda implements StatementVisitor{
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void visit(LambdaExpression lambdaExpression) {
|
public void visit(LambdaExpression lambdaExpression) {
|
||||||
// TODO Auto-generated method stub
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void visit(Assign assign) {
|
public void visit(Assign assign) {
|
||||||
// TODO Auto-generated method stub
|
assign.rightSide.accept(this);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -45,8 +52,9 @@ public class BytecodeGenLambda implements StatementVisitor{
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void visit(Block block) {
|
public void visit(Block block) {
|
||||||
// TODO Auto-generated method stub
|
for(Statement stmt : block.getStatements()) {
|
||||||
|
stmt.accept(this);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -63,8 +71,7 @@ public class BytecodeGenLambda implements StatementVisitor{
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void visit(FieldVar fieldVar) {
|
public void visit(FieldVar fieldVar) {
|
||||||
// TODO Auto-generated method stub
|
fieldVar.receiver.accept(this);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -99,8 +106,7 @@ public class BytecodeGenLambda implements StatementVisitor{
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void visit(MethodCall methodCall) {
|
public void visit(MethodCall methodCall) {
|
||||||
// TODO Auto-generated method stub
|
methodCall.receiver.accept(this);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -117,14 +123,12 @@ public class BytecodeGenLambda implements StatementVisitor{
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void visit(ExpressionReceiver receiver) {
|
public void visit(ExpressionReceiver receiver) {
|
||||||
// TODO Auto-generated method stub
|
receiver.expr.accept(this);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void visit(Return aReturn) {
|
public void visit(Return aReturn) {
|
||||||
// TODO Auto-generated method stub
|
aReturn.retexpr.accept(this);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -147,8 +151,8 @@ public class BytecodeGenLambda implements StatementVisitor{
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void visit(This aThis) {
|
public void visit(This aThis) {
|
||||||
// TODO Auto-generated method stub
|
this.isInstanceCapturingLambda = true;
|
||||||
|
this.argumentList.add(aThis.getType());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
11
test/bytecode/DuMethod.jav
Normal file
11
test/bytecode/DuMethod.jav
Normal file
@ -0,0 +1,11 @@
|
|||||||
|
public class DuMethod{
|
||||||
|
|
||||||
|
method(a){
|
||||||
|
return a;
|
||||||
|
}
|
||||||
|
|
||||||
|
method(a){
|
||||||
|
return a;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
8
test/bytecode/EmptyMethod.jav
Normal file
8
test/bytecode/EmptyMethod.jav
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
public class EmptyMethod{
|
||||||
|
|
||||||
|
public void m1(){
|
||||||
|
System.out.println("test");
|
||||||
|
}
|
||||||
|
|
||||||
|
public void m2(){}
|
||||||
|
}
|
14
test/bytecode/Faculty.jav
Normal file
14
test/bytecode/Faculty.jav
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
class Faculty {
|
||||||
|
|
||||||
|
Integer mul(Integer x, Integer y) {
|
||||||
|
return x;
|
||||||
|
}
|
||||||
|
|
||||||
|
m () {
|
||||||
|
|
||||||
|
var fact = (Integer x) -> {
|
||||||
|
return mul(x, x);
|
||||||
|
};
|
||||||
|
return fact;
|
||||||
|
}
|
||||||
|
}
|
10
test/bytecode/Faculty2.jav
Normal file
10
test/bytecode/Faculty2.jav
Normal file
@ -0,0 +1,10 @@
|
|||||||
|
class Faculty2 {
|
||||||
|
|
||||||
|
m () {
|
||||||
|
|
||||||
|
var fact = (Integer x) -> {
|
||||||
|
return x;
|
||||||
|
};
|
||||||
|
return fact;
|
||||||
|
}
|
||||||
|
}
|
@ -3,6 +3,8 @@ package bytecode;
|
|||||||
import de.dhbwstuttgart.bytecode.BytecodeGen;
|
import de.dhbwstuttgart.bytecode.BytecodeGen;
|
||||||
import de.dhbwstuttgart.core.JavaTXCompiler;
|
import de.dhbwstuttgart.core.JavaTXCompiler;
|
||||||
import de.dhbwstuttgart.syntaxtree.SourceFile;
|
import de.dhbwstuttgart.syntaxtree.SourceFile;
|
||||||
|
import de.dhbwstuttgart.typeinference.result.ResultPair;
|
||||||
|
import de.dhbwstuttgart.typeinference.result.ResultSet;
|
||||||
import org.junit.Test;
|
import org.junit.Test;
|
||||||
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
@ -27,14 +29,20 @@ public class JavaTXCompilerTest {
|
|||||||
@Test
|
@Test
|
||||||
public void test() throws IOException, java.lang.ClassNotFoundException {
|
public void test() throws IOException, java.lang.ClassNotFoundException {
|
||||||
System.out.println(rootDirectory);
|
System.out.println(rootDirectory);
|
||||||
String fileName = "LamRunnable";
|
String fileName = "DuMethod";
|
||||||
filesToTest.add(new File(rootDirectory+fileName+".jav"));
|
filesToTest.add(new File(rootDirectory+fileName+".jav"));
|
||||||
System.out.println(rootDirectory+fileName+".jav");
|
System.out.println(rootDirectory+fileName+".jav");
|
||||||
JavaTXCompiler compiler = new JavaTXCompiler(filesToTest);
|
JavaTXCompiler compiler = new JavaTXCompiler(filesToTest);
|
||||||
System.out.println("test");
|
System.out.println("test");
|
||||||
for(File f : filesToTest){
|
for(File f : filesToTest){
|
||||||
String content = readFile(f.getPath(), StandardCharsets.UTF_8);
|
String content = readFile(f.getPath(), StandardCharsets.UTF_8);
|
||||||
HashMap<String,byte[]> bytecode = this.getBytecode(compiler.sourceFiles.get(f));
|
List<ResultSet> typeinferenceResult = compiler.typeInference();
|
||||||
|
HashMap<String,byte[]> bytecode = this.getBytecode(compiler.sourceFiles.get(f), typeinferenceResult.get(0));
|
||||||
|
|
||||||
|
for(ResultPair ep : typeinferenceResult.get(0).results) {
|
||||||
|
System.out.println(ep.getLeft() + " ->" + ep.getRight());
|
||||||
|
}
|
||||||
|
|
||||||
String name = "";
|
String name = "";
|
||||||
int pos = f.getName().lastIndexOf(".");
|
int pos = f.getName().lastIndexOf(".");
|
||||||
if(pos != -1) {
|
if(pos != -1) {
|
||||||
@ -46,9 +54,9 @@ public class JavaTXCompilerTest {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public HashMap<String,byte[]> getBytecode(SourceFile sf) {
|
public HashMap<String,byte[]> getBytecode(SourceFile sf, ResultSet resultSet) {
|
||||||
HashMap<String,byte[]> classFiles = new HashMap<>();
|
HashMap<String,byte[]> classFiles = new HashMap<>();
|
||||||
BytecodeGen bytecodeGen = new BytecodeGen(classFiles);
|
BytecodeGen bytecodeGen = new BytecodeGen(classFiles,resultSet);
|
||||||
bytecodeGen.visit(sf);
|
bytecodeGen.visit(sf);
|
||||||
return bytecodeGen.getClassFiles();
|
return bytecodeGen.getClassFiles();
|
||||||
}
|
}
|
||||||
|
9
test/bytecode/LamAssign.jav
Normal file
9
test/bytecode/LamAssign.jav
Normal file
@ -0,0 +1,9 @@
|
|||||||
|
class LamAssign {
|
||||||
|
|
||||||
|
m () {
|
||||||
|
var lam1 = (Integer x) -> {
|
||||||
|
return x;
|
||||||
|
};
|
||||||
|
return lam1;
|
||||||
|
}
|
||||||
|
}
|
18
test/bytecode/Lambda.jav
Normal file
18
test/bytecode/Lambda.jav
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
class Lambda{
|
||||||
|
|
||||||
|
methode(){
|
||||||
|
return ((f) -> f);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/*
|
||||||
|
interface Fun0<A>{
|
||||||
|
A apply();
|
||||||
|
}
|
||||||
|
|
||||||
|
interface Fun1<A,B>{
|
||||||
|
A apply(B b);
|
||||||
|
}
|
||||||
|
*/
|
||||||
|
interface Fun2<A,B,C>{
|
||||||
|
A apply(B b, C c);
|
||||||
|
}
|
32
test/bytecode/Lambda2.jav
Normal file
32
test/bytecode/Lambda2.jav
Normal file
@ -0,0 +1,32 @@
|
|||||||
|
|
||||||
|
public class Lambda2
|
||||||
|
{
|
||||||
|
public static void main(List<String> args){
|
||||||
|
var listOfStrings = new List<String>();
|
||||||
|
var listOfObjects;
|
||||||
|
listOfObjects = map(listOfStrings, (a) -> a);
|
||||||
|
}
|
||||||
|
|
||||||
|
public map(a , b){
|
||||||
|
b.apply(a);
|
||||||
|
return a;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
public static <I,O> List<O> map(List<I> input, Function<I,O> func) {
|
||||||
|
List<O> output;
|
||||||
|
output = new List<O>();
|
||||||
|
output.add(func.apply(input.get()));
|
||||||
|
return output;
|
||||||
|
}
|
||||||
|
*/
|
||||||
|
}
|
||||||
|
|
||||||
|
class List<A>{
|
||||||
|
A get();
|
||||||
|
void add(A);
|
||||||
|
}
|
||||||
|
|
||||||
|
class Function<A,B>{
|
||||||
|
B apply(A a);
|
||||||
|
}
|
23
test/bytecode/Lambda3.jav
Normal file
23
test/bytecode/Lambda3.jav
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
|
||||||
|
public class Lambda2
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
public static <A> List<A> map(List<? extends A> input,
|
||||||
|
Function<? super A, ? extends A> func){
|
||||||
|
input.add(func.apply(input.get()));
|
||||||
|
}
|
||||||
|
*/
|
||||||
|
public map(input,func){
|
||||||
|
input.add(func.apply(input.get()));
|
||||||
|
return map(new List<String>(), func);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class List<A>{
|
||||||
|
A get();
|
||||||
|
void add(A);
|
||||||
|
}
|
||||||
|
|
||||||
|
class Function<A,B>{
|
||||||
|
B apply(A a);
|
||||||
|
}
|
6
test/bytecode/ReturnMethod.jav
Normal file
6
test/bytecode/ReturnMethod.jav
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
class ReturnMethod{
|
||||||
|
Integer r;
|
||||||
|
Integer mul(Integer x, Integer y) {
|
||||||
|
return r;
|
||||||
|
}
|
||||||
|
}
|
@ -1,6 +1,6 @@
|
|||||||
public class LamRun{
|
public class LamRun{
|
||||||
|
|
||||||
public LamRun(){
|
public void mRun(){
|
||||||
|
|
||||||
Runnable lam = () -> System.out.println("lambda");
|
Runnable lam = () -> System.out.println("lambda");
|
||||||
lam.run();
|
lam.run();
|
||||||
|
@ -5,6 +5,7 @@ public static void main(String[] a){
|
|||||||
//test if statement
|
//test if statement
|
||||||
//new TestIf(new Boolean(true));
|
//new TestIf(new Boolean(true));
|
||||||
// test lambda
|
// test lambda
|
||||||
new TestClass();
|
//new TestClass();
|
||||||
|
new LamRun();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
6
testBytecode/manually/Fac1.java
Normal file
6
testBytecode/manually/Fac1.java
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
class Fuc1{
|
||||||
|
|
||||||
|
Integer mul(Integer x, Integer y) {
|
||||||
|
return x;
|
||||||
|
}
|
||||||
|
}
|
14
testBytecode/manually/Fac2.java
Normal file
14
testBytecode/manually/Fac2.java
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
import java.util.function.Function;
|
||||||
|
class Fac2 {
|
||||||
|
|
||||||
|
Integer mul(Integer x, Integer y) {
|
||||||
|
return x;
|
||||||
|
}
|
||||||
|
|
||||||
|
Function<Integer,Integer> m () {
|
||||||
|
Function<Integer,Integer> fact = (Integer x) -> {
|
||||||
|
return mul(x, x);
|
||||||
|
};
|
||||||
|
return fact;
|
||||||
|
}
|
||||||
|
}
|
10
testBytecode/manually/LamAssign.java
Normal file
10
testBytecode/manually/LamAssign.java
Normal file
@ -0,0 +1,10 @@
|
|||||||
|
import java.util.function.Function;
|
||||||
|
class LamAssign {
|
||||||
|
|
||||||
|
Function<Integer,Integer> m () {
|
||||||
|
Function<Integer,Integer> lam1 = (Integer x) -> {
|
||||||
|
return x;
|
||||||
|
};
|
||||||
|
return lam1;
|
||||||
|
}
|
||||||
|
}
|
12
testBytecode/manually/LamAssignWithM.java
Normal file
12
testBytecode/manually/LamAssignWithM.java
Normal file
@ -0,0 +1,12 @@
|
|||||||
|
import java.util.function.Function;
|
||||||
|
class LamAssignWithM {
|
||||||
|
Integer mul(Integer x, Integer y) {
|
||||||
|
return x;
|
||||||
|
}
|
||||||
|
Function<Integer,Integer> m () {
|
||||||
|
Function<Integer,Integer> lam1 = (Integer x) -> {
|
||||||
|
return mul(x,x);
|
||||||
|
};
|
||||||
|
return lam1;
|
||||||
|
}
|
||||||
|
}
|
14
testBytecode/manually/LamWithAnField.java
Normal file
14
testBytecode/manually/LamWithAnField.java
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
import java.util.function.Function;
|
||||||
|
class LamWithAnField {
|
||||||
|
Integer mul(Integer x, Integer y) {
|
||||||
|
return x;
|
||||||
|
}
|
||||||
|
LamWithField temp= new LamWithField();
|
||||||
|
Function<Integer,Integer> m () {
|
||||||
|
Function<Integer,Integer> lam1 = (Integer x) -> {
|
||||||
|
return temp.res*x;
|
||||||
|
};
|
||||||
|
return lam1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
14
testBytecode/manually/LamWithField.java
Normal file
14
testBytecode/manually/LamWithField.java
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
import java.util.function.Function;
|
||||||
|
class LamWithField {
|
||||||
|
Integer mul(Integer x, Integer y) {
|
||||||
|
return x;
|
||||||
|
}
|
||||||
|
Integer res = new Integer(5);
|
||||||
|
Function<Integer,Integer> m () {
|
||||||
|
Function<Integer,Integer> lam1 = (Integer x) -> {
|
||||||
|
return res*x;
|
||||||
|
};
|
||||||
|
return lam1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
6
testBytecode/manually/ReturnM1.java
Normal file
6
testBytecode/manually/ReturnM1.java
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
class ReturnM1{
|
||||||
|
Integer r;
|
||||||
|
Integer mul(Integer x, Integer y) {
|
||||||
|
return r;
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user