All Downloads are FREE. Search and download functionalities are using the official Maven repository.

boomerang.weights.PathTrackingWeight Maven / Gradle / Ivy

There is a newer version: 3.2.2
Show newest version
package boomerang.weights;

import boomerang.scene.ControlFlowGraph.Edge;
import boomerang.scene.Val;
import com.google.common.collect.Lists;
import com.google.common.collect.Sets;
import java.util.LinkedHashSet;
import java.util.List;
import java.util.Set;
import sync.pds.solver.nodes.Node;
import wpds.impl.Weight;

public class PathTrackingWeight extends Weight {

  private static PathTrackingWeight one;
  /**
   * This set keeps track of all statements on a shortest path that use an alias from source to
   * sink.
   */
  private LinkedHashSet> shortestPathWitness = new LinkedHashSet<>();
  /**
   * This set keeps track of all statement along all paths that use an alias from source to sink.
   */
  private Set>> allPathWitness = Sets.newHashSet();

  private String rep;

  private PathTrackingWeight(String rep) {
    this.rep = rep;
  }

  private PathTrackingWeight(
      LinkedHashSet> allStatement,
      Set>> allPathWitness) {
    this.shortestPathWitness = allStatement;
    this.allPathWitness = allPathWitness;
  }

  public PathTrackingWeight(Node relevantStatement) {
    this.shortestPathWitness.add(relevantStatement);
    LinkedHashSet> firstDataFlowPath = new LinkedHashSet<>();
    firstDataFlowPath.add(relevantStatement);
    this.allPathWitness.add(firstDataFlowPath);
  }

  public static PathTrackingWeight one() {
    if (one == null) {
      one = new PathTrackingWeight("ONE");
    }
    return one;
  }

  @Override
  public Weight extendWith(Weight o) {
    if (!(o instanceof PathTrackingWeight))
      throw new RuntimeException("Cannot extend to different types of weight!");
    PathTrackingWeight other = (PathTrackingWeight) o;
    LinkedHashSet> newAllStatements = new LinkedHashSet<>();
    newAllStatements.addAll(shortestPathWitness);
    newAllStatements.addAll(other.shortestPathWitness);

    Set>> newAllPathStatements = new LinkedHashSet<>();
    for (LinkedHashSet> pathPrefix : allPathWitness) {
      for (LinkedHashSet> pathSuffix : other.allPathWitness) {
        LinkedHashSet> combinedPath = Sets.newLinkedHashSet();
        combinedPath.addAll(pathPrefix);
        combinedPath.addAll(pathSuffix);
        newAllPathStatements.add(combinedPath);
      }
    }
    if (allPathWitness.isEmpty()) {
      for (LinkedHashSet> pathSuffix : other.allPathWitness) {
        LinkedHashSet> combinedPath = Sets.newLinkedHashSet();
        combinedPath.addAll(pathSuffix);
        newAllPathStatements.add(combinedPath);
      }
    }
    if (other.allPathWitness.isEmpty()) {
      for (LinkedHashSet> pathSuffix : allPathWitness) {
        LinkedHashSet> combinedPath = Sets.newLinkedHashSet();
        combinedPath.addAll(pathSuffix);
        newAllPathStatements.add(combinedPath);
      }
    }

    return new PathTrackingWeight(newAllStatements, newAllPathStatements);
  }

  @Override
  public Weight combineWith(Weight o) {
    if (!(o instanceof PathTrackingWeight))
      throw new RuntimeException("Cannot extend to different types of weight!");
    PathTrackingWeight other = (PathTrackingWeight) o;
    Set>> newAllPathStatements = new LinkedHashSet<>();
    for (LinkedHashSet> pathPrefix : allPathWitness) {
      LinkedHashSet> combinedPath = Sets.newLinkedHashSet();
      combinedPath.addAll(pathPrefix);
      newAllPathStatements.add(combinedPath);
    }
    for (LinkedHashSet> pathPrefix : other.allPathWitness) {
      LinkedHashSet> combinedPath = Sets.newLinkedHashSet();
      combinedPath.addAll(pathPrefix);
      newAllPathStatements.add(combinedPath);
    }

    if (shortestPathWitness.size() > other.shortestPathWitness.size()) {
      return new PathTrackingWeight(
          new LinkedHashSet<>(other.shortestPathWitness), newAllPathStatements);
    }

    return new PathTrackingWeight(
        new LinkedHashSet<>(this.shortestPathWitness), newAllPathStatements);
  }

  @Override
  public int hashCode() {
    final int prime = 31;
    int result = 1;
    result = prime * result + ((shortestPathWitness == null) ? 0 : shortestPathWitness.hashCode());
    result = prime * result + ((rep == null) ? 0 : rep.hashCode());
    return result;
  }

  @Override
  public boolean equals(Object obj) {
    if (this == obj) return true;
    if (obj == null) return false;
    if (getClass() != obj.getClass()) return false;
    PathTrackingWeight other = (PathTrackingWeight) obj;
    if (shortestPathWitness == null) {
      if (other.shortestPathWitness != null) return false;
    } else if (!shortestPathWitness.equals(other.shortestPathWitness)) return false;
    if (allPathWitness == null) {
      if (other.allPathWitness != null) return false;
    } else if (!allPathWitness.equals(other.allPathWitness)) return false;
    if (rep == null) {
      if (other.rep != null) return false;
    } else if (!rep.equals(other.rep)) return false;
    return true;
  }

  @Override
  public String toString() {
    return "\nAll statements: " + shortestPathWitness;
  }

  public List> getShortestPathWitness() {
    return Lists.newArrayList(shortestPathWitness);
  }

  public Set>> getAllPathWitness() {
    return Sets.newHashSet(allPathWitness);
  }
}




© 2015 - 2025 Weber Informatics LLC | Privacy Policy