Git Product home page Git Product logo

jimpleframework's Introduction

JimpleFramework

Build Status

A Rascal implementation of the Jimple framework. The current version supports:

  • parsing Java Byte Code into a JIMPLE representation.
  • JIMPLE code optmization constructs.
  • a framework for dataflow analysis.

Requirements

  • Java ?
  • Maven
  • Rascal
  • Eclipse IDE
  • Lombok

Setting up your requirements

  1. Make sure Eclipse is running on Java ?. Also, you need to setup your PATH to use Java ? when using Maven.
  2. Install Lombok into Eclipse IDE. https://projectlombok.org/setup/eclipse

Installation Procedure

jimpleframework's People

Contributors

dependabot[bot] avatar faustocarva avatar jclavo avatar mateusluizfb avatar medisco avatar phtcosta avatar rbonifacio avatar waltim avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar

jimpleframework's Issues

Identity statement with incorrect local name

The identity statement of jimple is getting an incorrect value for local name.
Sample code:

class O {
	public O f;
}
public class FooBar {
	public static void main(String[] args) {
		O p = new O();
		O q = p;
		O r = new O();
		p.f = r;
		O t = bar(q);
	}
	static O bar(O s) {
		return s.f;
	}
}

Output from the decompiler module (only for the bar method):

    static samples.pointsto.ex2.O bar(samples.pointsto.ex2.O) 
    {
        samples.pointsto.ex2.O r1;
        samples.pointsto.ex2.O $r1;     
        i1 := @parameter0: samples.pointsto.ex2.O;     
        $r1 = r1.<samples.pointsto.ex2.O: samples.pointsto.ex2.O f>;   
        return $r1; 
    }

As you can see, there is no i1 variable in this scope.

Error in Decompiler class when processing classes with java 8 stream mechanism

Hi, the decompile method in Decompiler class is generating an error when processing classes with java stream mechanism.
Below the code to reproduce the error:

package samples;

import java.util.Arrays;
import java.util.List; 

public class StreamSupportSample {

	public static void main(String[] args) {

		List<String> myList = Arrays.asList("a1", "a2", "b1", "c2", "c1");

		myList.stream().filter(s -> s.startsWith("c")).map(String::toUpperCase).sorted().forEach(System.out::println);
		
	}

}

Error message:

-------------------------------------------------------
 T E S T S
-------------------------------------------------------
Running lang.jimple.internal.TestDecompiler
java.util.EmptyStackException
	at java.util.Stack.peek(Stack.java:102)
	at java.util.Stack.pop(Stack.java:84)
	at lang.jimple.internal.Decompiler$InstructionSetVisitor.invokeMethodIns(Decompiler.java:669)
	at lang.jimple.internal.Decompiler$InstructionSetVisitor.visitMethodInsn(Decompiler.java:529)
	at org.objectweb.asm.tree.MethodInsnNode.accept(Unknown Source)
	at org.objectweb.asm.tree.InsnList.accept(Unknown Source)
	at lang.jimple.internal.Decompiler$GenerateJimpleClassVisitor.visitMethod(Decompiler.java:203)
	at lang.jimple.internal.Decompiler$GenerateJimpleClassVisitor.visitEnd(Decompiler.java:154)

Code to test the class:

	@Test 
	public void decompileStreamSupport() {
		try {
			File classFile = new File("./target/test-classes/samples/StreamSupportSample.class"); 			
			assertNotNull(classFile);
			
			IValueFactory vf = ValueFactory.getInstance();
			Decompiler decompiler = new Decompiler(vf);
			IConstructor c = decompiler.decompile(new FileInputStream(classFile), null);
			
			assertNotNull(c);
		}
		catch(Exception e) {
			e.printStackTrace();
			fail(e.getLocalizedMessage());
		}
	}	

Error when decompiling specific test case

When we try to decompile this code:

public class Vanilla {
	public static void main(String[] args) {
		List<Student> students = Collections.emptyList();
		students.add(new Student("Pedro", 30));
		students.add(new Student("João", 25));
		
		Predicate<Student> p = s -> s.name == "Pedro";
		
		Vanilla v = new Vanilla();
		
	}
	
	public List<Student> vanilla(List<Student> students, Predicate<Student> p, Function<Student, Student> f) {
		List<Student> result = Collections.emptyList();
		boolean over = false;
		
		while(!over) {
			List<Student> sub = auxState.subList(0, auxState.size());
			
			if(p.test(auxState.get(0))) {
				result.add(f.apply(auxState.get(0)));
			}
			
			auxState = sub;
                }
		
		return result;
	}
	
	public List<Student> withFStream(List<Student> students, Predicate<Student> p, Function<Student, Student> f) {
		return Collections.emptyList();
	}

An exception occurs:

java.util.EmptyStackException
	at java.base/java.util.Stack.peek(Stack.java:102)
	at java.base/java.util.Stack.pop(Stack.java:84)
	at lang.jimple.internal.Decompiler$InstructionSetVisitor.returnIns(Decompiler.java:1269)

Wrong label name/target when decompiling code with lookupswitch/tableSwitch

The Compiler is generating random label targets when dealing with switch statements.
Example code:

  public void tableSwitch() {
    int a = 1;
    switch (a) {
      case 1:
        System.out.println(a);
      case 2:
        System.out.println(a);
      default:
        System.out.println(a);
    }
  }

The above code should generate the Jimple output bellow:

        lookupswitch(1)
	{
            case 1: goto label1;
            case 2: goto label2;
            default: goto label3;
        };

But it is generating this:

        lookupswitch($i1)
        {
            case 1: goto L2002984510;
            case 2: goto L300974586;
            default: goto L1929121194;
        }

The abstract representation from this input is:

          lookupSwitch(
            local("$i1"),
            [
              caseOption(1,"L189513712"),
              caseOption(2,"L717799000"),
              defaultOption("L1955752771")
            ]),

Variables names in jimple (from Bytecode) with duplicate entries

There is a bug in the Decompiler module that is creating duplicated variables names in some method bodies.
Sample Code:

package samples;
public class LongValueSample {
	public static void addLongValues() throws Exception {
		long x = 10L; 
		long y = 20L; 
		System.out.println(x + y);
	}
}

The Decompiler generates the code bellow:

    public static void addLongValues() throws java.lang.Exception
    {
        long $i2;
        long $i1;
        java.io.PrintStream $i2;
        long $i3;
     
        $i1 = 10L;
        $i2 = 20L;
        $i2 = <java.lang.System: java.io.PrintStream out>;
        $i3 = $i1 + $i2;
        virtualinvoke $i2.<java.io.PrintStream: void println(long)>($i3);
     
        return; 
    }

You can see the repeated usage of variable name $i2 (for a long and for java.io.PrintStream) .

Error when processing branches in Decompiler

An exception is thrown whenever we generate a control flow graph processing a code like:

public void equals() {
    int a = 5;
    int b = 5;
    boolean result = (a == b);
    System.out.println(result);
  }

The problem actually is with the decompiler.

Call to sensitive APIs

A new analysis to mine calls to sensitive APIs. Some tasks:

  • We have to find out how to model the sensitive APIs (e.g., a list of signatures)
  • We have to find a good case study (e.g., Android), and then use a corresponding list of sensitive APIs
  • We have to implement the algorithm to find calls to sensitive APIs

inadequate package decomposition

Currently, our organization in terms of packages is as follows:

io (IO utility functions for traversing the file system)
lang.jimple (AST + Decompiler)
lang.jimple.analysis (ControlFlowGraph)
lang.jimple.analysis.dataflow (DataFlow framework + DataFlow algorithms)
lang.jimple.analysis.ssa (conversion to the SSA format)
lang.jimple.core (execution context of the program analysis)
lang.jimple.internal (internal utility module for generating Java code from Jimple syntax)
lang.jimple.toolkit (CallGraph, SensitiveAnalysis, Global PP)
lang.jimple.toolkit.jimplify (Transformations for jimple code refinement)
lang.jimple.util (data type converterds (e.g.: signature to string) + Local PP)

We do think that the following is better:

lang.jimple.core: AST + ExecutionContext 
lang.jimple.toolkit: SSA, CallGraph, ControlFlowGraph
lang.jimple.analysys.dataflow: DataflowFramework + DataFlow algorithms
lang.jimple.analysys.security: SensitiveAnalysis
lang.jimple.decompiler: Decompiler, jimple transformations
lang.jimple.util: io, converters, ....

Error when decompiling code without the local-variable-table

We use the local-variable-table to configure the set of local variables of a method (including the corresponding type). Nonetheless, this table is only available when the source code of a system has been compiled using the -g (which sets debugging information).

Tasks:

  • Find a possible alternative to this problem
  • Implement the fix
  • Investigate if the implicit parameter + the formal arguments are being properly assigned to the local variables

Error when decompiling code with reflection call.

Hi, the decompile method in Decompiler class is generating an error when processing classes with java reflection mechanism.
Below is the code to reproduce the error:

public class Reflection {
	
  public static void staticInvokeReflection() throws NoSuchMethodException {
    // Invoking static method using reflection
    Method method = A.class.getMethod("staticFoo");
    try {
      method.invoke(null);
    } catch (IllegalAccessException e) {
      e.printStackTrace();
    } catch (InvocationTargetException e) {
      e.printStackTrace();
    }
  }
}

The A.java file:

public class A {
	public static void staticFoo() {
		System.out.println("foo");
	}
}

Error message:

-------------------------------------------------------
 T E S T S
-------------------------------------------------------
Running lang.jimple.internal.TestDecompiler
java.lang.ClassCastException: lang.jimple.internal.generated.Immediate$c_iValue cannot be cast to lang.jimple.internal.generated.Immediate$c_local
	at lang.jimple.internal.Decompiler$InstructionSetVisitor.invokeMethodIns(Decompiler.java:698)
	at lang.jimple.internal.Decompiler$InstructionSetVisitor.visitMethodInsn(Decompiler.java:555)
	at org.objectweb.asm.tree.MethodInsnNode.accept(Unknown Source)
	at org.objectweb.asm.tree.InsnList.accept(Unknown Source)
	at lang.jimple.internal.Decompiler$GenerateJimpleClassVisitor.visitMethod(Decompiler.java:210)
	at lang.jimple.internal.Decompiler$GenerateJimpleClassVisitor.visitEnd(Decompiler.java:162)
	at org.objectweb.asm.ClassReader.accept(Unknown Source)

Decompiling nested interfaces that spawns multiple class files

Hi, the Decompiler class has a problem when decompiling (bytecode to jimple) a class file that is originated from a source code (.java) which have a nested interface. Maybe the whole problem is related to the generation of multiples class files originated from java files. Below is the code that gives the error:

package samples;

interface MyInterfaceA{  
    void display();  
}  
      
class NestedInterface 
    implements MyInterfaceA{  
     public void display(){
         System.out.println("Nested interface method");
     }  
      
     public static void main(String args[]){  
         MyInterfaceA obj=
                 new NestedInterface(); 
      obj.display();  
     }  
}

I created a test case for this:

	@Test 
	public void decompileNestedInterface() {
		try {
			File classFile = new File("./target/test-classes/samples/NestedInterface.class"); 			
			assertNotNull(classFile);
			
			IValueFactory vf = ValueFactory.getInstance();
			Decompiler decompiler = new Decompiler(vf);
			IConstructor c = decompiler.decompile(new FileInputStream(classFile), null);
			
			assertNotNull(c);
		}
		catch(Exception e) {
			e.printStackTrace();
			fail(e.getLocalizedMessage());
		}
	}

And here the error:

-------------------------------------------------------
 T E S T S
-------------------------------------------------------
Running lang.jimple.internal.TestDecompiler
Tests run: 5, Failures: 0, Errors: 1, Skipped: 0, Time elapsed: 0.226 sec <<< FAILURE!
decompileNestedInterface(lang.jimple.internal.TestDecompiler)  Time elapsed: 0.023 sec  <<< ERROR!
java.lang.StackOverflowError
	at lang.jimple.internal.JimpleObjectFactory.type(JimpleObjectFactory.java:107)
	at lang.jimple.internal.JimpleObjectFactory.type(JimpleObjectFactory.java:127)
	at lang.jimple.internal.JimpleObjectFactory.type(JimpleObjectFactory.java:127)
	at lang.jimple.internal.JimpleObjectFactory.type(JimpleObjectFactory.java:127)

I came up with this error trying to process this simple file:

https://github.com/OpenFeign/feign/blob/819b2df8c54d9266abf4cde9b17ab7890ed95cc6/core/src/main/java/feign/stream/StreamDecoder.java

  • this code spawns to class files, one for StreamDecoder and other for the stream used inside.

Error Error in Decompiler class when processing for loop over an interface (collection)

Sample code to reproduce the error:

public class TestClass {
	public void D() {	
		List<String> list = List.of("a","b","c","d");
		for(int i=0; i < list.size(); i++) {
			log("Executing D: "+list.get(i));
		}
	}

        static void log(String message) {
		System.out.println(message);
	}
}

Error message:

java.lang.StackOverflowError
	at lang.jimple.internal.JimpleObjectFactory.type(JimpleObjectFactory.java:107)
	at lang.jimple.internal.JimpleObjectFactory.type(JimpleObjectFactory.java:127)
	at lang.jimple.internal.JimpleObjectFactory.type(JimpleObjectFactory.java:127)
	at lang.jimple.internal.JimpleObjectFactory.type(JimpleObjectFactory.java:127)
	at lang.jimple.internal.JimpleObjectFactory.type(JimpleObjectFactory.java:127)

Error running a specific algorithm

When running this java code:

// Source: https://www.w3resource.com/java-exercises/math/java-math-exercise-20.php
public class GeneratePrimes {
	public static int [] generatePrimes(int num) {
	    boolean[] temp = new boolean[num + 1];
	    for (int i = 2; i * i <= num; i++) {
	        if (!temp [i]) {
	            for (int j = i; i * j <= num; j++) {
	                temp [i*j] = true;
	            }
	        }
	    }
	    int prime_nums = 0;
	    for (int i = 2; i <= num; i++) {
	        if (!temp [i]) prime_nums++;
	    }
	    int [] all_primes = new int [prime_nums];
	    int index = 0; 
	    for (int i = 2; i <= num; i++) {
	        if (!temp [i]) all_primes [index++] = i;
	    }
	    return all_primes;
	}
}

This error was raised:

Screen Shot 2021-03-11 at 19 58 25

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.