// Copyright 2015 the V8 project authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

var DEFAULT_NODE_ROW_SEPARATION = 130

var traceLayout = false;

function newGraphOccupation(graph){
  var isSlotFilled = [];
  var maxSlot = 0;
  var minSlot = 0;
  var nodeOccupation = [];

  function slotToIndex(slot) {
    if (slot >= 0) {
      return slot * 2;
    } else {
      return slot * 2 + 1;
    }
  }

  function indexToSlot(index) {
    if ((index % 0) == 0) {
      return index / 2;
    } else {
      return -((index - 1) / 2);
    }
  }

  function positionToSlot(pos) {
    return Math.floor(pos / NODE_INPUT_WIDTH);
  }

  function slotToLeftPosition(slot) {
    return slot * NODE_INPUT_WIDTH
  }

  function slotToRightPosition(slot) {
    return (slot + 1) * NODE_INPUT_WIDTH
  }

  function findSpace(pos, width, direction) {
    var widthSlots = Math.floor((width + NODE_INPUT_WIDTH - 1) /
                                NODE_INPUT_WIDTH);
    var currentSlot = positionToSlot(pos + width / 2);
    var currentScanSlot = currentSlot;
    var widthSlotsRemainingLeft = widthSlots;
    var widthSlotsRemainingRight = widthSlots;
    var slotsChecked = 0;
    while (true) {
      var mod = slotsChecked++ % 2;
      currentScanSlot = currentSlot + (mod ? -1 : 1) * (slotsChecked >> 1);
      if (!isSlotFilled[slotToIndex(currentScanSlot)]) {
        if (mod) {
          if (direction <= 0) --widthSlotsRemainingLeft
        } else {
          if (direction >= 0) --widthSlotsRemainingRight
        }
        if (widthSlotsRemainingLeft == 0 ||
            widthSlotsRemainingRight == 0 ||
            (widthSlotsRemainingLeft + widthSlotsRemainingRight) == widthSlots &&
            (widthSlots == slotsChecked)) {
          if (mod) {
            return [currentScanSlot, widthSlots];
          } else {
            return [currentScanSlot - widthSlots + 1, widthSlots];
          }
        }
      } else {
        if (mod) {
          widthSlotsRemainingLeft = widthSlots;
        } else {
          widthSlotsRemainingRight = widthSlots;
        }
      }
    }
  }

  function setIndexRange(from, to, value) {
    if (to < from) {
      throw("illegal slot range");
    }
    while (from <= to) {
      if (from > maxSlot) {
        maxSlot = from;
      }
      if (from < minSlot) {
        minSlot = from;
      }
      isSlotFilled[slotToIndex(from++)] = value;
    }
  }

  function occupySlotRange(from, to) {
    if (traceLayout) {
      console.log("Occupied [" + slotToLeftPosition(from) + "  " + slotToLeftPosition(to + 1) + ")");
    }
    setIndexRange(from, to, true);
  }

  function clearSlotRange(from, to) {
    if (traceLayout) {
      console.log("Cleared [" + slotToLeftPosition(from) + "  " + slotToLeftPosition(to + 1) + ")");
    }
    setIndexRange(from, to, false);
  }

  function occupyPositionRange(from, to) {
    occupySlotRange(positionToSlot(from), positionToSlot(to - 1));
  }

  function clearPositionRange(from, to) {
    clearSlotRange(positionToSlot(from), positionToSlot(to - 1));
  }

  function occupyPositionRangeWithMargin(from, to, margin) {
    var fromMargin = from - Math.floor(margin);
    var toMargin = to + Math.floor(margin);
    occupyPositionRange(fromMargin, toMargin);
  }

  function clearPositionRangeWithMargin(from, to, margin) {
    var fromMargin = from - Math.floor(margin);
    var toMargin = to + Math.floor(margin);
    clearPositionRange(fromMargin, toMargin);
  }

  var occupation = {
    occupyNodeInputs: function(node) {
      for (var i = 0; i < node.inputs.length; ++i) {
        if (node.inputs[i].isVisible()) {
          var edge = node.inputs[i];
          if (!edge.isBackEdge()) {
            var source = edge.source;
            var horizontalPos = edge.getInputHorizontalPosition(graph);
            if (traceLayout) {
              console.log("Occupying input " + i + " of " + node.id + " at " + horizontalPos);
            }
            occupyPositionRangeWithMargin(horizontalPos,
                                          horizontalPos,
                                          NODE_INPUT_WIDTH / 2);
          }
        }
      }
    },
    occupyNode: function(node) {
      var getPlacementHint = function(n) {
        var pos = 0;
        var direction = -1;
        var outputEdges = 0;
        var inputEdges = 0;
        for (var k = 0; k < n.outputs.length; ++k) {
          var outputEdge = n.outputs[k];
          if (outputEdge.isVisible()) {
            var output = n.outputs[k].target;
            for (var l = 0; l < output.inputs.length; ++l) {
              if (output.rank > n.rank) {
                var inputEdge = output.inputs[l];
                if (inputEdge.isVisible()) {
                  ++inputEdges;
                }
                if (output.inputs[l].source == n) {
                  pos += output.x + output.getInputX(l) + NODE_INPUT_WIDTH / 2;
                  outputEdges++;
                  if (l >= (output.inputs.length / 2)) {
                    direction = 1;
                  }
                }
              }
            }
          }
        }
        if (outputEdges != 0) {
          pos = pos / outputEdges;
        }
        if (outputEdges > 1 || inputEdges == 1) {
          direction = 0;
        }
        return [direction, pos];
      }
      var width = node.getTotalNodeWidth();
      var margin = MINIMUM_EDGE_SEPARATION;
      var paddedWidth = width + 2 * margin;
      var placementHint = getPlacementHint(node);
      var x = placementHint[1] - paddedWidth + margin;
      if (traceLayout) {
        console.log("Node " + node.id + " placement hint [" + x + ", " + (x + paddedWidth) + ")");
      }
      var placement = findSpace(x, paddedWidth, placementHint[0]);
      var firstSlot = placement[0];
      var slotWidth = placement[1];
      var endSlotExclusive = firstSlot + slotWidth - 1;
      occupySlotRange(firstSlot, endSlotExclusive);
      nodeOccupation.push([firstSlot, endSlotExclusive]);
      if (placementHint[0] < 0) {
        return slotToLeftPosition(firstSlot + slotWidth) - width - margin;
      } else if (placementHint[0] > 0) {
        return slotToLeftPosition(firstSlot) + margin;
      } else {
        return slotToLeftPosition(firstSlot + slotWidth / 2) - (width / 2);
      }
    },
    clearOccupiedNodes: function() {
      nodeOccupation.forEach(function(o) {
        clearSlotRange(o[0], o[1]);
      });
      nodeOccupation = [];
    },
    clearNodeOutputs: function(source) {
      source.outputs.forEach(function(edge) {
        if (edge.isVisible()) {
          var target = edge.target;
          for (var i = 0; i < target.inputs.length; ++i) {
            if (target.inputs[i].source === source) {
              var horizontalPos = edge.getInputHorizontalPosition(graph);
              clearPositionRangeWithMargin(horizontalPos,
                                           horizontalPos,
                                           NODE_INPUT_WIDTH / 2);
            }
          }
        }
      });
    },
    print: function() {
      var s = "";
      for (var currentSlot = -40; currentSlot < 40; ++currentSlot) {
        if (currentSlot != 0) {
          s += " ";
        } else {
          s += "|";
        }
      }
      console.log(s);
      s = "";
      for (var currentSlot2 = -40; currentSlot2 < 40; ++currentSlot2) {
        if (isSlotFilled[slotToIndex(currentSlot2)]) {
          s += "*";
        } else {
          s += " ";
        }
      }
      console.log(s);
    }
  }
  return occupation;
}

function layoutNodeGraph(graph) {
  // First determine the set of nodes that have no outputs. Those are the
  // basis for bottom-up DFS to determine rank and node placement.
  var endNodesHasNoOutputs = [];
  var startNodesHasNoInputs = [];
  graph.nodes.forEach(function(n, i){
    endNodesHasNoOutputs[n.id] = true;
    startNodesHasNoInputs[n.id] = true;
  });
  graph.edges.forEach(function(e, i){
    endNodesHasNoOutputs[e.source.id] = false;
    startNodesHasNoInputs[e.target.id] = false;
  });

  // Finialize the list of start and end nodes.
  var endNodes = [];
  var startNodes = [];
  var visited = [];
  var rank = [];
  graph.nodes.forEach(function(n, i){
    if (endNodesHasNoOutputs[n.id]) {
      endNodes.push(n);
    }
    if (startNodesHasNoInputs[n.id]) {
      startNodes.push(n);
    }
    visited[n.id] = false;
    rank[n.id] = -1;
    n.rank = 0;
    n.visitOrderWithinRank = 0;
    n.outputApproach = MINIMUM_NODE_OUTPUT_APPROACH;
  });


  var maxRank = 0;
  var visited = [];
  var dfsStack = [];
  var visitOrderWithinRank = 0;

  var worklist = startNodes.slice();
  while (worklist.length != 0) {
    var n = worklist.pop();
    var changed = false;
    if (n.rank == MAX_RANK_SENTINEL) {
      n.rank = 1;
      changed = true;
    }
    var begin = 0;
    var end = n.inputs.length;
    if (n.opcode == 'Phi' || n.opcode == 'EffectPhi') {
      // Keep with merge or loop node
      begin = n.inputs.length - 1;
    } else if (n.hasBackEdges()) {
      end = 1;
    }
    for (var l = begin; l < end; ++l) {
      var input = n.inputs[l].source;
      if (input.visible && input.rank >= n.rank) {
        n.rank = input.rank + 1;
        changed = true;
      }
    }
    if (changed) {
      var hasBackEdges = n.hasBackEdges();
      for (var l = n.outputs.length - 1; l >= 0; --l) {
        if (hasBackEdges && (l != 0)) {
          worklist.unshift(n.outputs[l].target);
        } else {
          worklist.push(n.outputs[l].target);
        }
      }
    }
    if (n.rank > maxRank) {
      maxRank = n.rank;
    }
  }

   visited = [];
  function dfsFindRankLate(n) {
    if (visited[n.id]) return;
    visited[n.id] = true;
    var originalRank = n.rank;
    var newRank = n.rank;
    var firstInput = true;
    for (var l = 0; l < n.outputs.length; ++l) {
      var output = n.outputs[l].target;
      dfsFindRankLate(output);
      var outputRank = output.rank;
      if (output.visible && (firstInput || outputRank <= newRank) &&
          (outputRank > originalRank)) {
        newRank = outputRank - 1;
      }
      firstInput = false;
    }
    if (n.opcode != "Start" && n.opcode != "Phi" && n.opcode != "EffectPhi") {
      n.rank = newRank;
    }
  }

  startNodes.forEach(dfsFindRankLate);

  visited = [];
  function dfsRankOrder(n) {
    if (visited[n.id]) return;
    visited[n.id] = true;
    for (var l = 0; l < n.outputs.length; ++l) {
      var edge = n.outputs[l];
      if (edge.isVisible()) {
        var output = edge.target;
        dfsRankOrder(output);
      }
    }
    if (n.visitOrderWithinRank == 0) {
      n.visitOrderWithinRank = ++visitOrderWithinRank;
    }
  }
  startNodes.forEach(dfsRankOrder);

  endNodes.forEach(function(n) {
    n.rank = maxRank + 1;
  });

  var rankSets = [];
  // Collect sets for each rank.
  graph.nodes.forEach(function(n, i){
    n.y = n.rank * (DEFAULT_NODE_ROW_SEPARATION + graph.getNodeHeight(n) +
                    2 * DEFAULT_NODE_BUBBLE_RADIUS);
    if (n.visible) {
      if (rankSets[n.rank] === undefined) {
        rankSets[n.rank] = [n];
      } else {
        rankSets[n.rank].push(n);
      }
    }
  });

  // Iterate backwards from highest to lowest rank, placing nodes so that they
  // spread out from the "center" as much as possible while still being
  // compact and not overlapping live input lines.
  var occupation = newGraphOccupation(graph);
  var rankCount = 0;

  rankSets.reverse().forEach(function(rankSet) {

    for (var i = 0; i < rankSet.length; ++i) {
      occupation.clearNodeOutputs(rankSet[i]);
    }

    if (traceLayout) {
      console.log("After clearing outputs");
      occupation.print();
    }

    var placedCount = 0;
    rankSet = rankSet.sort(function(a,b) {
      return a.visitOrderWithinRank < b.visitOrderWithinRank;
    });
    for (var i = 0; i < rankSet.length; ++i) {
      var nodeToPlace = rankSet[i];
      if (nodeToPlace.visible) {
        nodeToPlace.x = occupation.occupyNode(nodeToPlace);
        if (traceLayout) {
          console.log("Node " + nodeToPlace.id + " is placed between [" + nodeToPlace.x + ", " + (nodeToPlace.x + nodeToPlace.getTotalNodeWidth()) + ")");
        }
        var staggeredFlooredI = Math.floor(placedCount++ % 3);
        var delta = MINIMUM_EDGE_SEPARATION * staggeredFlooredI
        nodeToPlace.outputApproach += delta;
      } else {
        nodeToPlace.x = 0;
      }
    }

    if (traceLayout) {
      console.log("Before clearing nodes");
      occupation.print();
    }

    occupation.clearOccupiedNodes();

    if (traceLayout) {
      console.log("After clearing nodes");
      occupation.print();
    }

    for (var i = 0; i < rankSet.length; ++i) {
      var node = rankSet[i];
      occupation.occupyNodeInputs(node);
    }

    if (traceLayout) {
      console.log("After occupying inputs");
      occupation.print();
    }

    if (traceLayout) {
      console.log("After determining bounding box");
      occupation.print();
    }
  });

  graph.maxBackEdgeNumber = 0;
  graph.visibleEdges.each(function (e) {
    if (e.isBackEdge()) {
      e.backEdgeNumber = ++graph.maxBackEdgeNumber;
    } else {
      e.backEdgeNumber = 0;
    }
  });

  redetermineGraphBoundingBox(graph);

}

function redetermineGraphBoundingBox(graph) {
  graph.minGraphX = 0;
  graph.maxGraphNodeX = 1;
  graph.maxGraphX = undefined;  // see below
  graph.minGraphY = 0;
  graph.maxGraphY = 1;

  for (var i = 0; i < graph.nodes.length; ++i) {
    var node = graph.nodes[i];

    if (!node.visible) {
      continue;
    }

    if (node.x < graph.minGraphX) {
      graph.minGraphX = node.x;
    }
    if ((node.x + node.getTotalNodeWidth()) > graph.maxGraphNodeX) {
      graph.maxGraphNodeX = node.x + node.getTotalNodeWidth();
    }
    if ((node.y - 50) < graph.minGraphY) {
      graph.minGraphY = node.y - 50;
    }
    if ((node.y + graph.getNodeHeight(node) + 50) > graph.maxGraphY) {
      graph.maxGraphY = node.y + graph.getNodeHeight(node) + 50;
    }
  }

  graph.maxGraphX = graph.maxGraphNodeX +
    graph.maxBackEdgeNumber * MINIMUM_EDGE_SEPARATION;

}
