I'm trying to write an analysis that checks that a class implements Comparable.compareTo
|java+method:///java/lang/Comparable/compareTo(T)|.
I tried playing with M3.methodOverrides, and in some cases it works. But with the code below, methodOverrides does not contain compareTo at all.
//Geometric.java
public interface Geometric extends Comparable<Geometric> {
public double area();
}
//Circle.java
public class Circle implements Geometric {
private double r;
private double x;
private double y;
public Circle(double x, double y, double r) {
this.x = x;
this.y = y;
this.r = r;
}
@Override
public double area() {
return Math.PI * Math.pow(r, 2);
}
@Override
public int compareTo(Geometric o) {
return (int) (area() - o.area());
}
@Override
public String toString() {
return "Circle...";
}
}
When loading these files using createM3FromDirectory
, M3.methodOverrides contains only a single entry:
<|java+method:///Circle/area()|,|java+method:///Geometric/area()|>
Is there a way to take some transitive closures of some relations in M3 to conclude that
|java+method:///Circle/compareTo(Geometric)|
overrides |java+method:///java/lang/Comparable/compareTo(T)|
?
I can't believe my eyes. I just tried it again, and now it works.
//Main.rsc
module Main
import IO;
import lang::java::m3::Core;
void main(list[str] args)
{
loc projectDir = |file:///| + args[0];
M3 model = createM3FromDirectory(projectDir);
for( ov <- model.methodOverrides ) { println(ov); }
}
Inside eclipse rascal console:
rascal>main(["/home/mkl/radboud/src/java-feedback/java-feedback-rascal/test-data/assignment03-override-not-detected"]);
Reloading module Main
<|java+method:///Circle/toString()|,|java+method:///java/lang/Object/toString()|>
<|java+method:///Circle/area()|,|java+method:///Geometric/area()|>
<|java+method:///Circle/compareTo(Geometric)|,|java+method:///java/lang/Comparable/compareTo(T)|>
There it is: Circle actually implements Comparable.compareTo.
<|java+method:///Circle/compareTo(Geometric)|,|java+method:///java/lang/Comparable/compareTo(T)|>
I think the problem was that I'm using two different versions of rascal. Rascal shell, which seems to be an older version, gives different results.
Using rascal-shell:
$ java -Xmx1G -Xss32m -jar ~/tmp/rascal-shell-stable.jar Main.rsc /home/mkl/radboud/src/java-feedback/java-feedback-rascal/test-data/assignment03-override-not-detected
Version: unknown
<|java+method:///Circle/area()|,|java+method:///Geometric/area()|>
I think I was only running rascal-shell. When running from inside eclipse, it gives the correct results.
As far as I'm concerned it works as expected.
P.S. I understand that M3 only records immediate facts, and that I have to calculate transitive closures myself when needed.