Beispiel #1
0
  public ListenableFuture<?> processFor(Duration duration) {
    checkLockNotHeld("Can not process for a duration while holding the driver lock");

    checkNotNull(duration, "duration is null");

    long maxRuntime = duration.roundTo(TimeUnit.NANOSECONDS);

    long start = System.nanoTime();
    do {
      ListenableFuture<?> future = process();
      if (!future.isDone()) {
        return future;
      }
    } while (System.nanoTime() - start < maxRuntime && !isFinished());

    return NOT_BLOCKED;
  }
Beispiel #2
0
  public boolean isFinished() {
    checkLockNotHeld("Can not check finished status while holding the driver lock");

    // if we can get the lock, attempt a clean shutdown; otherwise someone else will shutdown
    try (DriverLockResult lockResult =
        tryLockAndProcessPendingStateChanges(0, TimeUnit.MILLISECONDS)) {
      if (lockResult.wasAcquired()) {
        boolean finished =
            state.get() != State.ALIVE
                || driverContext.isDone()
                || operators.get(operators.size() - 1).isFinished();
        if (finished) {
          state.compareAndSet(State.ALIVE, State.NEED_DESTRUCTION);
        }
        return finished;
      } else {
        // did not get the lock, so we can't check operators, or destroy
        return state.get() != State.ALIVE || driverContext.isDone();
      }
    }
  }
Beispiel #3
0
  public void updateSource(TaskSource source) {
    checkLockNotHeld("Can not update sources while holding the driver lock");

    // does this driver have an operator for the specified source?
    if (!sourceOperators.containsKey(source.getPlanNodeId())) {
      return;
    }

    // stage the new updates
    while (true) {
      // attempt to update directly to the new source
      TaskSource currentNewSource = newSources.putIfAbsent(source.getPlanNodeId(), source);

      // if update succeeded, just break
      if (currentNewSource == null) {
        break;
      }

      // merge source into the current new source
      TaskSource newSource = currentNewSource.update(source);

      // if this is not a new source, just return
      if (newSource == currentNewSource) {
        break;
      }

      // attempt to replace the currentNewSource with the new source
      if (newSources.replace(source.getPlanNodeId(), currentNewSource, newSource)) {
        break;
      }

      // someone else updated while we were processing
    }

    // attempt to get the lock and process the updates we staged above
    // updates will be processed in close if and only if we got the lock
    tryLockAndProcessPendingStateChanges(0, TimeUnit.MILLISECONDS).close();
  }
Beispiel #4
0
  private DriverLockResult tryLockAndProcessPendingStateChanges(int timeout, TimeUnit unit) {
    checkLockNotHeld("Can not acquire the driver lock while already holding the driver lock");

    return new DriverLockResult(timeout, unit);
  }
Beispiel #5
0
  public ListenableFuture<?> process() {
    checkLockNotHeld("Can not process while holding the driver lock");

    try (DriverLockResult lockResult =
        tryLockAndProcessPendingStateChanges(100, TimeUnit.MILLISECONDS)) {
      try {
        if (!lockResult.wasAcquired()) {
          // this is unlikely to happen unless the driver is being
          // destroyed and in that case the caller should notice notice
          // this state change by calling isFinished
          return NOT_BLOCKED;
        }

        driverContext.start();

        if (!newSources.isEmpty()) {
          processNewSources();
        }

        for (int i = 0; i < operators.size() - 1 && !driverContext.isDone(); i++) {
          // check if current operator is blocked
          Operator current = operators.get(i);
          ListenableFuture<?> blocked = current.isBlocked();
          if (!blocked.isDone()) {
            current.getOperatorContext().recordBlocked(blocked);
            return blocked;
          }

          // check if next operator is blocked
          Operator next = operators.get(i + 1);
          blocked = next.isBlocked();
          if (!blocked.isDone()) {
            next.getOperatorContext().recordBlocked(blocked);
            return blocked;
          }

          // if current operator is finished...
          if (current.isFinished()) {
            // let next operator know there will be no more data
            next.getOperatorContext().startIntervalTimer();
            next.finish();
            next.getOperatorContext().recordFinish();
          } else {
            // if next operator needs input...
            if (next.needsInput()) {
              // get an output page from current operator
              current.getOperatorContext().startIntervalTimer();
              Page page = current.getOutput();
              current.getOperatorContext().recordGetOutput(page);

              // if we got an output page, add it to the next operator
              if (page != null) {
                next.getOperatorContext().startIntervalTimer();
                next.addInput(page);
                next.getOperatorContext().recordAddInput(page);
              }
            }
          }
        }
        return NOT_BLOCKED;
      } catch (Throwable t) {
        driverContext.failed(t);
        throw t;
      }
    }
  }