package com.ikea.shared.util;

import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;
import java.lang.reflect.Array;
import java.util.AbstractQueue;
import java.util.Collection;
import java.util.Iterator;
import java.util.NoSuchElementException;
import java.util.concurrent.BlockingQueue;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.ReentrantLock;

public class LinkedBlockingDeque<E> extends AbstractQueue<E>
  implements BlockingQueue<E>, Serializable
{
  private static final long serialVersionUID = -387911632671998426L;
  protected final int capacity;
  private transient int count;
  private transient Node<E> first;
  private transient Node<E> last;
  protected final ReentrantLock lock = new ReentrantLock();
  private final Condition notEmpty = this.lock.newCondition();
  private final Condition notFull = this.lock.newCondition();

  public LinkedBlockingDeque()
  {
    this(2147483647);
  }

  public LinkedBlockingDeque(int paramInt)
  {
    if (paramInt <= 0)
      throw new IllegalArgumentException();
    this.capacity = paramInt;
  }

  public LinkedBlockingDeque(Collection<? extends E> paramCollection)
  {
    this(2147483647);
    Iterator localIterator = paramCollection.iterator();
    while (localIterator.hasNext())
      add(localIterator.next());
  }

  private boolean linkFirst(E paramE)
  {
    if (this.count >= this.capacity)
      return false;
    this.count = (1 + this.count);
    Node localNode1 = this.first;
    Node localNode2 = new Node(paramE, null, localNode1);
    this.first = localNode2;
    if (this.last == null)
      this.last = localNode2;
    while (true)
    {
      this.notEmpty.signal();
      return true;
      localNode1.prev = localNode2;
    }
  }

  private boolean linkLast(E paramE)
  {
    if (this.count >= this.capacity)
      return false;
    this.count = (1 + this.count);
    Node localNode1 = this.last;
    Node localNode2 = new Node(paramE, localNode1, null);
    this.last = localNode2;
    if (this.first == null)
      this.first = localNode2;
    while (true)
    {
      this.notEmpty.signal();
      return true;
      localNode1.next = localNode2;
    }
  }

  private void readObject(ObjectInputStream paramObjectInputStream)
    throws IOException, ClassNotFoundException
  {
    paramObjectInputStream.defaultReadObject();
    this.count = 0;
    this.first = null;
    this.last = null;
    while (true)
    {
      Object localObject = paramObjectInputStream.readObject();
      if (localObject == null)
        return;
      add(localObject);
    }
  }

  private void unlink(Node<E> paramNode)
  {
    Node localNode1 = paramNode.prev;
    Node localNode2 = paramNode.next;
    if (localNode1 == null)
      if (localNode2 == null)
      {
        this.last = null;
        this.first = null;
      }
    while (true)
    {
      this.count = (-1 + this.count);
      this.notFull.signalAll();
      return;
      localNode2.prev = null;
      this.first = localNode2;
      continue;
      if (localNode2 == null)
      {
        localNode1.next = null;
        this.last = localNode1;
      }
      else
      {
        localNode1.next = localNode2;
        localNode2.prev = localNode1;
      }
    }
  }

  private E unlinkFirst()
  {
    Node localNode1 = this.first;
    if (localNode1 == null)
      return null;
    Node localNode2 = localNode1.next;
    this.first = localNode2;
    if (localNode2 == null)
      this.last = null;
    while (true)
    {
      this.count = (-1 + this.count);
      this.notFull.signal();
      return localNode1.item;
      localNode2.prev = null;
    }
  }

  private E unlinkLast()
  {
    Node localNode1 = this.last;
    if (localNode1 == null)
      return null;
    Node localNode2 = localNode1.prev;
    this.last = localNode2;
    if (localNode2 == null)
      this.first = null;
    while (true)
    {
      this.count = (-1 + this.count);
      this.notFull.signal();
      return localNode1.item;
      localNode2.next = null;
    }
  }

  private void writeObject(ObjectOutputStream paramObjectOutputStream)
    throws IOException
  {
    this.lock.lock();
    try
    {
      paramObjectOutputStream.defaultWriteObject();
      for (Node localNode = this.first; localNode != null; localNode = localNode.next)
        paramObjectOutputStream.writeObject(localNode.item);
      paramObjectOutputStream.writeObject(null);
      return;
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public boolean add(E paramE)
  {
    addLast(paramE);
    return true;
  }

  public void addFirst(E paramE)
  {
    if (!offerFirst(paramE))
      throw new IllegalStateException("Deque full");
  }

  public void addLast(E paramE)
  {
    if (!offerLast(paramE))
      throw new IllegalStateException("Deque full");
  }

  public void clear()
  {
    this.lock.lock();
    try
    {
      this.last = null;
      this.first = null;
      this.count = 0;
      this.notFull.signalAll();
      return;
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public boolean contains(Object paramObject)
  {
    if (paramObject == null)
      return false;
    this.lock.lock();
    try
    {
      for (Node localNode = this.first; localNode != null; localNode = localNode.next)
      {
        boolean bool = paramObject.equals(localNode.item);
        if (bool)
          return true;
      }
      return false;
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public Iterator<E> descendingIterator()
  {
    return new DescendingItr(null);
  }

  public int drainTo(Collection<? super E> paramCollection)
  {
    if (paramCollection == null)
      throw new NullPointerException();
    if (paramCollection == this)
      throw new IllegalArgumentException();
    this.lock.lock();
    try
    {
      for (Node localNode = this.first; localNode != null; localNode = localNode.next)
        paramCollection.add(localNode.item);
      int i = this.count;
      this.count = 0;
      this.last = null;
      this.first = null;
      this.notFull.signalAll();
      return i;
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public int drainTo(Collection<? super E> paramCollection, int paramInt)
  {
    if (paramCollection == null)
      throw new NullPointerException();
    if (paramCollection == this)
      throw new IllegalArgumentException();
    this.lock.lock();
    int i = 0;
    while (true)
    {
      if (i < paramInt);
      try
      {
        if (this.first != null)
        {
          paramCollection.add(this.first.item);
          this.first.prev = null;
          this.first = this.first.next;
          this.count = (-1 + this.count);
          i++;
          continue;
        }
        if (this.first == null)
          this.last = null;
        this.notFull.signalAll();
        return i;
      }
      finally
      {
        this.lock.unlock();
      }
    }
  }

  public E element()
  {
    return getFirst();
  }

  public E getFirst()
  {
    Object localObject = peekFirst();
    if (localObject == null)
      throw new NoSuchElementException();
    return localObject;
  }

  public E getLast()
  {
    Object localObject = peekLast();
    if (localObject == null)
      throw new NoSuchElementException();
    return localObject;
  }

  public Iterator<E> iterator()
  {
    return new Itr(null);
  }

  public boolean offer(E paramE)
  {
    return offerLast(paramE);
  }

  public boolean offer(E paramE, long paramLong, TimeUnit paramTimeUnit)
    throws InterruptedException
  {
    return offerLast(paramE, paramLong, paramTimeUnit);
  }

  public boolean offerFirst(E paramE)
  {
    if (paramE == null)
      throw new NullPointerException();
    this.lock.lock();
    try
    {
      boolean bool = linkFirst(paramE);
      return bool;
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public boolean offerFirst(E paramE, long paramLong, TimeUnit paramTimeUnit)
    throws InterruptedException
  {
    if (paramE == null)
      throw new NullPointerException();
    long l1 = paramTimeUnit.toNanos(paramLong);
    this.lock.lockInterruptibly();
    try
    {
      while (true)
      {
        boolean bool = linkFirst(paramE);
        if (bool)
          return true;
        if (l1 <= 0L)
          return false;
        long l2 = this.notFull.awaitNanos(l1);
        l1 = l2;
      }
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public boolean offerLast(E paramE)
  {
    if (paramE == null)
      throw new NullPointerException();
    this.lock.lock();
    try
    {
      boolean bool = linkLast(paramE);
      return bool;
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public boolean offerLast(E paramE, long paramLong, TimeUnit paramTimeUnit)
    throws InterruptedException
  {
    if (paramE == null)
      throw new NullPointerException();
    long l1 = paramTimeUnit.toNanos(paramLong);
    this.lock.lockInterruptibly();
    try
    {
      while (true)
      {
        boolean bool = linkLast(paramE);
        if (bool)
          return true;
        if (l1 <= 0L)
          return false;
        long l2 = this.notFull.awaitNanos(l1);
        l1 = l2;
      }
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public E peek()
  {
    return peekFirst();
  }

  public E peekFirst()
  {
    this.lock.lock();
    try
    {
      Node localNode = this.first;
      if (localNode == null);
      for (Object localObject2 = null; ; localObject2 = this.first.item)
        return localObject2;
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public E peekLast()
  {
    this.lock.lock();
    try
    {
      Node localNode = this.last;
      if (localNode == null);
      for (Object localObject2 = null; ; localObject2 = this.last.item)
        return localObject2;
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public E poll()
  {
    return pollFirst();
  }

  public E poll(long paramLong, TimeUnit paramTimeUnit)
    throws InterruptedException
  {
    return pollFirst(paramLong, paramTimeUnit);
  }

  public E pollFirst()
  {
    this.lock.lock();
    try
    {
      Object localObject2 = unlinkFirst();
      return localObject2;
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public E pollFirst(long paramLong, TimeUnit paramTimeUnit)
    throws InterruptedException
  {
    long l1 = paramTimeUnit.toNanos(paramLong);
    this.lock.lockInterruptibly();
    try
    {
      while (true)
      {
        Object localObject2 = unlinkFirst();
        if (localObject2 != null)
          return localObject2;
        if (l1 <= 0L)
          return null;
        long l2 = this.notEmpty.awaitNanos(l1);
        l1 = l2;
      }
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public E pollLast()
  {
    this.lock.lock();
    try
    {
      Object localObject2 = unlinkLast();
      return localObject2;
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public E pollLast(long paramLong, TimeUnit paramTimeUnit)
    throws InterruptedException
  {
    long l1 = paramTimeUnit.toNanos(paramLong);
    this.lock.lockInterruptibly();
    try
    {
      while (true)
      {
        Object localObject2 = unlinkLast();
        if (localObject2 != null)
          return localObject2;
        if (l1 <= 0L)
          return null;
        long l2 = this.notEmpty.awaitNanos(l1);
        l1 = l2;
      }
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public E pop()
  {
    return removeFirst();
  }

  public void push(E paramE)
  {
    addFirst(paramE);
  }

  public void put(E paramE)
    throws InterruptedException
  {
    putLast(paramE);
  }

  public void putFirst(E paramE)
    throws InterruptedException
  {
    if (paramE == null)
      throw new NullPointerException();
    this.lock.lock();
    try
    {
      if (!linkFirst(paramE))
        this.notFull.await();
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public void putLast(E paramE)
    throws InterruptedException
  {
    if (paramE == null)
      throw new NullPointerException();
    this.lock.lock();
    try
    {
      if (!linkLast(paramE))
        this.notFull.await();
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public int remainingCapacity()
  {
    this.lock.lock();
    try
    {
      int i = this.capacity;
      int j = this.count;
      int k = i - j;
      return k;
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public E remove()
  {
    return removeFirst();
  }

  public boolean remove(Object paramObject)
  {
    return removeFirstOccurrence(paramObject);
  }

  public E removeFirst()
  {
    Object localObject = pollFirst();
    if (localObject == null)
      throw new NoSuchElementException();
    return localObject;
  }

  public boolean removeFirstOccurrence(Object paramObject)
  {
    if (paramObject == null)
      return false;
    this.lock.lock();
    try
    {
      for (Node localNode = this.first; localNode != null; localNode = localNode.next)
        if (paramObject.equals(localNode.item))
        {
          unlink(localNode);
          return true;
        }
      return false;
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public E removeLast()
  {
    Object localObject = pollLast();
    if (localObject == null)
      throw new NoSuchElementException();
    return localObject;
  }

  public boolean removeLastOccurrence(Object paramObject)
  {
    if (paramObject == null)
      return false;
    this.lock.lock();
    try
    {
      for (Node localNode = this.last; localNode != null; localNode = localNode.prev)
        if (paramObject.equals(localNode.item))
        {
          unlink(localNode);
          return true;
        }
      return false;
    }
    finally
    {
      this.lock.unlock();
    }
  }

  boolean removeNode(Node<E> paramNode)
  {
    this.lock.lock();
    try
    {
      for (Node localNode = this.first; localNode != null; localNode = localNode.next)
        if (localNode.equals(paramNode))
        {
          unlink(localNode);
          return true;
        }
      return false;
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public int size()
  {
    this.lock.lock();
    try
    {
      int i = this.count;
      return i;
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public E take()
    throws InterruptedException
  {
    return takeFirst();
  }

  public E takeFirst()
    throws InterruptedException
  {
    this.lock.lock();
    Object localObject2;
    try
    {
      while (true)
      {
        localObject2 = unlinkFirst();
        if (localObject2 != null)
          break;
        this.notEmpty.await();
      }
    }
    finally
    {
      this.lock.unlock();
    }
    this.lock.unlock();
    return localObject2;
  }

  public E takeLast()
    throws InterruptedException
  {
    this.lock.lock();
    Object localObject2;
    try
    {
      while (true)
      {
        localObject2 = unlinkLast();
        if (localObject2 != null)
          break;
        this.notEmpty.await();
      }
    }
    finally
    {
      this.lock.unlock();
    }
    this.lock.unlock();
    return localObject2;
  }

  public Object[] toArray()
  {
    this.lock.lock();
    try
    {
      Object[] arrayOfObject = new Object[this.count];
      Node localNode = this.first;
      int j;
      for (int i = 0; localNode != null; i = j)
      {
        j = i + 1;
        arrayOfObject[i] = localNode.item;
        localNode = localNode.next;
      }
      return arrayOfObject;
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public <T> T[] toArray(T[] paramArrayOfT)
  {
    this.lock.lock();
    try
    {
      if (paramArrayOfT.length < this.count)
        paramArrayOfT = (Object[])Array.newInstance(paramArrayOfT.getClass().getComponentType(), this.count);
      Node localNode = this.first;
      int j;
      for (int i = 0; localNode != null; i = j)
      {
        j = i + 1;
        paramArrayOfT[i] = localNode.item;
        localNode = localNode.next;
      }
      if (paramArrayOfT.length > i)
        paramArrayOfT[i] = null;
      return paramArrayOfT;
    }
    finally
    {
      this.lock.unlock();
    }
  }

  public String toString()
  {
    this.lock.lock();
    try
    {
      String str = super.toString();
      return str;
    }
    finally
    {
      this.lock.unlock();
    }
  }

  private abstract class AbstractItr
    implements Iterator<E>
  {
    private LinkedBlockingDeque.Node<E> lastRet;
    LinkedBlockingDeque.Node<E> next;
    E nextItem;

    AbstractItr()
    {
      advance();
    }

    abstract void advance();

    public boolean hasNext()
    {
      return this.next != null;
    }

    public E next()
    {
      if (this.next == null)
        throw new NoSuchElementException();
      this.lastRet = this.next;
      Object localObject = this.nextItem;
      advance();
      return localObject;
    }

    public void remove()
    {
      LinkedBlockingDeque.Node localNode = this.lastRet;
      if (localNode == null)
        throw new IllegalStateException();
      this.lastRet = null;
      LinkedBlockingDeque.this.removeNode(localNode);
    }
  }

  private class DescendingItr extends LinkedBlockingDeque<E>.AbstractItr
  {
    private DescendingItr()
    {
      super();
    }

    void advance()
    {
      ReentrantLock localReentrantLock = LinkedBlockingDeque.this.lock;
      localReentrantLock.lock();
      try
      {
        LinkedBlockingDeque.Node localNode;
        if (this.next == null)
        {
          localNode = LinkedBlockingDeque.this.last;
          this.next = localNode;
          if (this.next != null)
            break label64;
        }
        label64: for (Object localObject2 = null; ; localObject2 = this.next.item)
        {
          this.nextItem = localObject2;
          return;
          localNode = this.next.prev;
          break;
        }
      }
      finally
      {
        localReentrantLock.unlock();
      }
    }
  }

  private class Itr extends LinkedBlockingDeque<E>.AbstractItr
  {
    private Itr()
    {
      super();
    }

    void advance()
    {
      ReentrantLock localReentrantLock = LinkedBlockingDeque.this.lock;
      localReentrantLock.lock();
      try
      {
        LinkedBlockingDeque.Node localNode;
        if (this.next == null)
        {
          localNode = LinkedBlockingDeque.this.first;
          this.next = localNode;
          if (this.next != null)
            break label64;
        }
        label64: for (Object localObject2 = null; ; localObject2 = this.next.item)
        {
          this.nextItem = localObject2;
          return;
          localNode = this.next.next;
          break;
        }
      }
      finally
      {
        localReentrantLock.unlock();
      }
    }
  }

  static final class Node<E>
  {
    E item;
    Node<E> next;
    Node<E> prev;

    Node(E paramE, Node<E> paramNode1, Node<E> paramNode2)
    {
      this.item = paramE;
      this.prev = paramNode1;
      this.next = paramNode2;
    }
  }
}

/* Location:           C:\Documents and Settings\Cesar Cabello Cea\Mis documentos\Downloads\apk-downloader\com.ikea.kompis-6_dex2jar.jar
 * Qualified Name:     com.ikea.shared.util.LinkedBlockingDeque
 * JD-Core Version:    0.6.2
 */