Пример #1
0
  protected RegionVar getUniqueRegionOf(Var var) {
    assert (var != null && varmap.get(var) != null)
        : " Var " + var + method + " " + var.getDeclaringMethod();
    Node node = (varmap.get(var)).get(null);
    if (node == null) return null;

    return node.getRep().getRegion();
  }
Пример #2
0
  protected List<RegionVar> getRegionsOf(Var var, Map<RegionVar, Set<Field>> dead) {
    Node node = (varmap.get(var)).get(null);
    if (node == null) return null;

    List<RegionVar> regions = new ArrayList<RegionVar>();
    getRegionsHelper(node.getRep(), dead, regions);
    return regions;
  }
Пример #3
0
 private void computeCaches() {
   cacheAllRegions = new ArrayList<RegionVar>();
   cacheI2R = new HashMap<Integer, RegionVar>();
   for (Node n : nodes) getRegionsHelper(n.getRep(), null, cacheAllRegions);
   for (RegionVar r : cacheAllRegions) {
     r.setIndex(++numRegions);
     cacheI2R.put(r.getIndex(), r);
   }
   numRegions++;
 }
Пример #4
0
  /* Matches the subgraphs rooted at two nodes and records the
   * isomorphism into a map. */
  private static void matchSubgraph(Node node1, Node node2, Map<RegionVar, RegionVar> map) {
    RegionVar r1 = node1.getRep().getRegion();
    RegionVar r2 = node2.getRep().getRegion();

    if (map.containsKey(r1)) {
      assert (r2 == map.get(r1))
          : "at call: "
              + node2.graph.method
              + " to "
              + node1.graph.method
              + "\n"
              + r2
              + "("
              + node2
              + ") vs "
              + map.get(r1)
              + " corresponding to "
              + r1
              + "("
              + node1
              + ")";
      return;
    }

    map.put(r1, r2);

    if (secondary_index[3]) {
      node1 = node1.getRep();
      node2 = node2.getRep();
      for (Field f : node1.outfields.keySet()) {
        FieldEdge fe1 = node1.outfields.get(f);
        assert (fe1.src == node1);
        FieldEdge fe2 = node2.outfields.get(f);
        assert (fe2 != null);
        matchSubgraph(fe1.dst, fe2.dst, map);
      }
    } else {
      for (Field f : node1.graph.fedges.keySet())
        for (FieldEdge fe1 : node1.graph.fedges.get(f)) {
          if (fe1.src != node1) continue;
          boolean found = false;
          assert (node2.graph.fedges.get(f) != null);
          for (FieldEdge fe2 : node2.graph.fedges.get(f)) {
            if (fe2.src != node2) continue;
            if (!fe1.field.equals(fe2.field)) continue;
            matchSubgraph(fe1.dst, fe2.dst, map);
            found = true;
            break;
          }
          assert (found);
        }
    }
  }
Пример #5
0
  /* Processing assignments of allocation statements. Left hand side
  is either a variable or the field of a variable. The right hand
  side is the allocation site, represented by the allocation
  instruction. */
  public void assignAlloc(Var x, Field f, New a) {

    Node nodeL = getNode(x, f);
    nodeL.hasallocs = true;
    nodeL.istouched = true;

    setTouched(x);

    if (IRHelper.isLibrary(method.getDeclaringClass())) nodeL.hasliballocs = true;

    Node nodeR = allocmap.get(a);
    assert (nodeR == null) : "Allocation site already entered";
    allocmap.put(a, nodeL);
  }
Пример #6
0
  protected void addRegionsFrom(
      Node node, Map<RegionVar, Set<Field>> dead, IBitVector<RegionVar> marked) {
    RegionVar reg = node.getRegion();
    if (reg.isHeap() || marked.get(reg)) return;

    marked.set(reg);
    if (secondary_index[6]) {
      for (Field f : node.getRep().outfields.keySet()) {
        FieldEdge fe = node.getRep().outfields.get(f);
        assert (fe.src == node);
        if (dead == null || dead.get(reg) == null || !dead.get(reg).contains(fe.field))
          addRegionsFrom(fe.dst.getRep(), dead, marked);
      }
    } else {
      for (Field f : fedges.keySet())
        for (FieldEdge fe : fedges.get(f)) {
          if (fe.src == node) {
            if (dead == null || dead.get(reg) == null || !dead.get(reg).contains(fe.field))
              addRegionsFrom(fe.dst, dead, marked);
          }
        }
    }
  }
Пример #7
0
  private void getRegionsHelper(
      Node node, Map<RegionVar, Set<Field>> dead, List<RegionVar> regions) {
    RegionVar reg = node.getRegion();
    if (regions.contains(reg)) return;

    regions.add(reg);
    if (secondary_index[6]) {
      for (Field f : node.getRep().outfields.keySet()) {
        FieldEdge fe = node.getRep().outfields.get(f);
        assert (fe.src == node);
        if (dead == null || dead.get(reg) == null || !dead.get(reg).contains(fe.field))
          getRegionsHelper(fe.dst.getRep(), dead, regions);
      }
    } else {
      for (Field f : fedges.keySet())
        for (FieldEdge fe : fedges.get(f)) {
          if (fe.src == node) {
            if (dead == null || dead.get(reg) == null || !dead.get(reg).contains(fe.field))
              getRegionsHelper(fe.dst, dead, regions);
          }
        }
    }
  }
Пример #8
0
  protected RegionVar getUniqueRegionOf(Node n, Field f) {
    if (secondary_index[5]) {
      FieldEdge fe = n.getRep().outfields.get(f);
      assert (fe != null && fe.src == n);
      return fe.dst.getRep().getRegion();
    }

    if (fedges.get(f) == null) return null;

    for (FieldEdge fe : fedges.get(f)) {
      assert (fe.field.equals(f));
      if (fe.src.equals(n)) return fe.dst.getRep().getRegion();
    }
    return null;
  }
Пример #9
0
  /** Is tag reachable from node on paths with no visited nodes? */
  private Node reachesTag(Node node, UniqueTag tag, Set<Node> visited) {
    assert (node.isRep());
    if (visited.contains(node)) return null;
    if (tag.mergeable(node.tag)) return node;

    visited.add(node);

    if (secondary_index[2]) {
      for (Field f : node.infields.keySet())
        for (FieldEdge e : node.infields.get(f)) {
          assert (e.dst == node);
          Node result = reachesTag(e.src.getRep(), tag, visited);
          if (result != null) return result;
        }
    } else {
      for (Field f : fedges.keySet())
        for (FieldEdge e : fedges.get(f)) {
          if (e.dst != node) continue;
          Node result = reachesTag(e.src, tag, visited);
          if (result != null) return result;
        }
    }
    return null;
  }
Пример #10
0
 protected int numTouched() {
   int c = 0;
   for (Node node : nodes) if (node.isRep() && node.isTouched()) c++;
   return c;
 }
Пример #11
0
 protected int numAlloc() {
   int c = 0;
   for (Node node : nodes) if (node.isRep() && node.hasAllocations()) c++;
   return c;
 }
Пример #12
0
 protected int numHeap() {
   int c = 0;
   for (Node node : nodes) if (node.isRep() && node.isHeap()) c++;
   return c;
 }
Пример #13
0
 protected void setGlobal(Var v) {
   Node node = getNode(v, null);
   assert (!v.isLocal() || v.isException());
   node.isheap = true;
 }
Пример #14
0
  /* Print the current type graph to the dotfile */
  public void printDot(String title, Call call) {
    boolean printUnifications = false;
    PrintStream ps = PointsToAnalysis.v().file;
    if (ps == null) return;

    ps.println("\ndigraph F {");
    ps.println("   size = \"7,7\"; rankdir = LR;");
    ps.println("   orientation = landscape;");

    ps.println("   subgraph cluster1 {");
    ps.println("   \"Method: " + method.getName() + "\" [color=white];");

    if (nodes.isEmpty()) {
      ps.println("   \"empty graph\" [color = white];");
      ps.println("   }");
      ps.println("}");
      return;
    }

    for (Node node : nodes) {
      if (!printUnifications && !node.isRep()) continue;
      String color = "style=filled,fillcolor=";
      if (node.isheap && node.hasallocs) color += "red,";
      else if (node.isheap) color += "orange,";
      else if (node.hasallocs) color += "grey,";
      else color += "white,";
      // if (node.istouched) color = "khaki";
      // if (node.hassync) color = "khaki";
      String shape = "shape=";
      if (node.istouched) shape += "box";
      else shape += "ellipse";

      ps.println("   o" + node.id + "[label = \"" + node.getName() + "\"," + color + shape + "];");
    }
    ps.println("   }");

    Map<Integer, Map<Integer, String>> labels = new HashMap<Integer, Map<Integer, String>>();
    for (Field f : fedges.keySet())
      for (FieldEdge e : fedges.get(f)) {
        if (labels.containsKey(e.src.id)) {
          if (labels.get(e.src.id).containsKey(e.dst.id)) {
            labels.get(e.src.id).put(e.dst.id, "*");
            //                            labels.get(e.src.id).get(e.dst.id) + ", " +
            //                            e.field.getName());
          } else labels.get(e.src.id).put(e.dst.id, e.field.getName());

        } else {
          Map<Integer, String> is = new HashMap<Integer, String>();
          is.put(e.dst.id, e.field.getName());
          labels.put(e.src.id, is);
        }
      }
    for (Integer i : labels.keySet())
      for (Integer j : labels.get(i).keySet())
        ps.print(
            "   o"
                + i
                + " -> o"
                + j
                + "[label=\""
                + labels.get(i).get(j)
                + "\",style=solid,color=black];");

    for (Call ce : cedges.keySet())
      for (CallEdge e : cedges.get(ce)) {
        if (!(e.call instanceof VirtualCallExpr)) continue;
        // if (!e.call.equals(call)) continue;
        ps.print(
            "   o"
                + e.src.id
                + " -> o"
                + e.dst.id
                + "[label=\""
                + e.call
                + "\",style=solid,color=red];");
      }

    if (printUnifications)
      for (Node node : nodes)
        if (node.parent != null)
          ps.println("   o" + node.id + " -> o" + node.parent.id + " [color = blue];");

    ps.println("}");
  }
Пример #15
0
 public void setTouched(Var x) {
   Node ni = getNode(x, null);
   ni.istouched = true;
 }
Пример #16
0
 /* Adds syncronization placed on an object */
 public void monitorUse(Var x) {
   Node ni = getNode(x, null);
   ni.hassync = true;
   ni.istouched = true;
 }
Пример #17
0
 protected RegionVar getUniqueRegionOf(VarF vf) {
   Node node = (varmap.get(vf.getVar())).get(vf.getField());
   if (node == null) return null;
   return node.getRep().getRegion();
 }
Пример #18
0
 /** Does the graph contain a node of a given tag? */
 private Node containsTag(UniqueTag tag) {
   for (Node node : nodes) if (node.isRep() && tag.mergeable(node.tag)) return node;
   return null;
 }
Пример #19
0
 protected int numSync() {
   int c = 0;
   for (Node node : nodes) if (node.isRep() && node.hasSync()) c++;
   return c;
 }
Пример #20
0
  /* process unification constraints */
  protected void process(UnifyConstraint c) {
    Node n1 = c.node1.getRep();
    Node n2 = c.node2.getRep();
    assert (n1.graph == this);
    assert (n2.graph == this);
    if (n1 == n2) return;

    if (heapfix && n2.isheap && !n1.isheap) {
      Node sw = n1;
      n1 = n2;
      n2 = sw;
    }

    n1.mergeTags(n2);
    n1.mergeFlags(n2);
    n2.parent = n1;
    n2.tag = null;
    n2.region = null;

    if (secondary_index[0]) {
      for (FieldEdge e : n2.outfields.values()) {
        assert (e.src == n2);
        if (e.dst == n2) w.addLast(new FieldConstraint(n1, n1, e.field));
        else {
          w.addLast(new FieldConstraint(n1, e.dst, e.field));
          e.dst.infields.get(e.field).remove(e);
        }
        fedges.get(e.field).remove(e);
      }

      for (Field f : n2.infields.keySet())
        for (FieldEdge e : n2.infields.get(f)) {
          assert (e.dst == n2);
          e.dst = n1;
          addInField(n1, f, e);
        }

      n2.outfields = null;
      n2.infields = null;
    } else {
      HashSet<FieldEdge> fremove = new HashSet<FieldEdge>();
      for (Field f : fedges.keySet()) {
        Collection<FieldEdge> fed = fedges.get(f);
        int size = fed.size();
        fremove.clear();
        for (FieldEdge e : fed) {
          if (e.src == n2) {
            if (e.dst == n2) w.addLast(new FieldConstraint(n1, n1, e.field));
            else w.addLast(new FieldConstraint(n1, e.dst, e.field));
          } else {
            if (e.dst == n2) e.dst = n1;
            continue;
          }
          if (!fremove.contains(e)) {
            fremove.add(e);
            size--;
          }
        }
        fed.removeAll(fremove);
        assert (fed.size() == size);
      }
    }

    HashSet<CallEdge> cremove = new HashSet<CallEdge>();
    for (Call ce : cedges.keySet()) {
      Collection<CallEdge> ced = cedges.get(ce);
      cremove.clear();
      int size = ced.size();
      for (CallEdge e : ced) {
        if (e.dst == n2) {
          if (e.src == n2) w.addLast(new CallConstraint(n1, n1, e.call));
          else w.addLast(new CallConstraint(e.src, n1, e.call));
        } else {
          if (e.src == n2) e.src = n1;
          continue;
        }
        if (!cremove.contains(e)) {
          cremove.add(e);
          size--;
        }
      }
      ced.removeAll(cremove);
      assert (ced.size() == size);
    }
  }
Пример #21
0
 /* Return the region of an allocation site in this method */
 protected RegionVar getAllocRegion(New alloc) {
   Node node = allocmap.get(alloc);
   assert (node != null);
   return node.getRep().getRegion();
 }