org.linkedin.util-core/src/main/java/org/linkedin/util/concurrent/ThreadControl.java
public Object block(Object key)
  {
    if(log.isDebugEnabled())
      log.debug(LangUtils.shortIdentityString(this) + ".block(" + key + ")");

    _lock.lock();
    try
    {
      _waitingForBlock.add(key);
      _blockCondition.signalAll();

      long endTime = System.currentTimeMillis() + _timeout.getDurationInMilliseconds();

      while(!_waitingForUnblock.containsKey(key))
      {
        try
        {
          ConcurrentUtils.awaitUntil(_unblockCondition, endTime);
        }
        catch(InterruptedException e)
        {
          throw new RuntimeException(e);
        }
        catch(TimeoutException e)
        {
          throw new RuntimeException(e);
        }
      }

      return _waitingForUnblock.remove(key);
    }
    finally
    {
      _lock.unlock();
    }
  }
public Object block(Object key)
  {
    if(log.isDebugEnabled())
      log.debug(LangUtils.shortIdentityString(this) + ".block(" + key + ")");

    _lock.lock();
    try
    {
      _waitingForBlock.add(key);
      _blockCondition.signalAll();

      long endTime = System.currentTimeMillis() + _timeout.getDurationInMilliseconds();

      while(!_waitingForUnblock.containsKey(key))
      {
        try
        {
          ConcurrentUtils.awaitUntil(_unblockCondition, endTime);
        }
        catch(InterruptedException e)
        {
          throw new RuntimeException(e);
        }
        catch(TimeoutException e)
        {
          throw new RuntimeException(e);
        }
      }

      return _waitingForUnblock.remove(key);
    }
    finally
    {
      _lock.unlock();
    }
  }
This method is usually called from within a mock object to execute the call associated
to the given key. It will block until another thread calls one of the <code>unblock</code>
method with the object to return.

@param key same key as used in <code>unblock</code>
@return the object provided to <code>unblock</code>