-
Notifications
You must be signed in to change notification settings - Fork 37
Expand file tree
/
Copy pathDuplicatedDeclarationHandler.java
More file actions
112 lines (95 loc) · 3.59 KB
/
DuplicatedDeclarationHandler.java
File metadata and controls
112 lines (95 loc) · 3.59 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
package br.ufpe.cin.mergers.handlers;
import java.util.ArrayList;
import java.util.List;
import org.eclipse.jdt.core.compiler.IProblem;
import br.ufpe.cin.files.FilesManager;
import br.ufpe.cin.mergers.util.JavaCompiler;
import br.ufpe.cin.mergers.util.MergeConflict;
import br.ufpe.cin.mergers.util.MergeContext;
import br.ufpe.cin.mergers.util.Source;
/**
* Unstructured merge added false negatives are mostly caused by failing to detect that the contributions to be merged add duplicated declarations.
* For example, unstructured merge reports no conflict when merging developers contributions that add declarations with the same signature to different areas of the same class.
* This handler detects such situations. Note that semistructured merge detects such false negatives without handlers, so this handler serves only for statistics purpose.
* @author Guilherme Cavalcanti
*/
public final class DuplicatedDeclarationHandler implements ConflictHandler {
public void handle(MergeContext context){
int duplicatedDeclarationErrors = 0;
long t0 = System.nanoTime();
//1. compile unstructured merge output
JavaCompiler compiler = new JavaCompiler();
compiler.compile(context, Source.UNSTRUCTURED);
//2. list its compilation problems
List<IProblem> iproblems = compiler.compilationProblems;
List<MyProblem> problems = filterDistinctProblems(iproblems);
//3. search and account duplicated declaration errors not surround by conflicts (otherwise, it would be not a false negative)
for(int i = 0; i<problems.size(); i++){
MyProblem problem = problems.get(i);
String problemMessage = problem.toString().toLowerCase();
if(problemMessage.contains("duplicate")){
if(!isConflictingLOC(context,problem.sourceLOCs)){
duplicatedDeclarationErrors++;
}
}
}
//excluding handler execution time to not bias peformance evaluation as it is not required to original semistructured merge time
long tf = System.nanoTime();
long tt = tf-t0;
context.semistructuredMergeTime = context.semistructuredMergeTime - tt;
context.duplicatedDeclarationErrors = duplicatedDeclarationErrors;
}
/**
* Aggregates compilations problems by its message and source line numbers.
* @param problems
*/
private static List<MyProblem> filterDistinctProblems(List<IProblem> problems) {
List<MyProblem> distinctproblems = new ArrayList<MyProblem>();
for(IProblem problem : problems){
boolean found = false;
for(MyProblem mp : distinctproblems){
if(mp.message.equals(problem.getMessage())){
mp.sourceLOCs.add(problem.getSourceLineNumber());
found = true;
}
}
if(!found){
MyProblem mp = new MyProblem(problem.getMessage(),problem.getSourceLineNumber());
distinctproblems.add(mp);
}
}
return distinctproblems;
}
/**
* Checks if at least one given source line number is surround by conflicts.
* @param context
* @param sourceLOCs
*/
private static boolean isConflictingLOC(MergeContext context, List<Integer> sourceLOCs) {
List<MergeConflict> conflicts = FilesManager.extractMergeConflicts(context.unstructuredOutput);
for(int sourceLOC : sourceLOCs){
for(MergeConflict mc : conflicts){
if((mc.getStartLOC() <= sourceLOC) && (mc.getEndLOC() >= sourceLOC)) {
return true;
}
}
}
return false;
}
}
/**
* Custom IProblem
* @author Guilherme Cavalcanti
*/
class MyProblem {
List<Integer> sourceLOCs = new ArrayList<Integer>();
String message = "";
public MyProblem(String message, int sourceLineNumber){
this.message = message;
this.sourceLOCs.add(sourceLineNumber);
}
@Override
public String toString() {
return this.message;
}
}