/** {@inheritDoc} */ public E pollAcquire(Object owner) { E element; // Find an element on the requeue that is free and return it. if (!requeue.isEmpty()) { for (RequeueElementWrapper<E> nextRecord : requeue) { if (AcquireState.Free.equals(nextRecord.state)) { nextRecord.state = AcquireState.Acquired; nextRecord.owner = owner; return nextRecord.element; } } } // Nothing could be found on the requeue, so attempt to poll an element off the main queue and // acquire // it on the requeue. element = queue.poll(); if (element != null) { requeue(element, owner, AcquireState.Acquired); } return element; }
/** * Places an element onto the requeue buffer, in the acquired state by the specified owner. * * @param element The element to place onto the requeue buffer. * @param owner The owner of the acquired element. * @param acquired The acquired state to set on the element in the requeue. * @return The requeue element wrapper for the requeued element. */ private RequeueElementWrapper<E> requeue(E element, Object owner, AcquireState acquired) { RequeueElementWrapper<E> record = new RequeueElementWrapper<E>(element); record.state = acquired; record.owner = owner; requeue.add(record); requeuedElementMap.put(element, record); return record; }
/** {@inheritDoc} */ public void release(Object owner, Object o) { // Look up the element wrapper record for the element to be released, and release it. RequeueElementWrapper<E> record = requeuedElementMap.get(o); if (record != null) { record.state = AcquireState.Free; record.owner = null; } }
/** {@inheritDoc} */ public boolean acquire(Object owner, Object o) { // Look up the element wrapper record for the element to be accepted. RequeueElementWrapper<E> record = requeuedElementMap.get(o); // Check if the element is currently free, and acquire it if so. if (AcquireState.Free.equals(record.state)) { record.state = AcquireState.Acquired; record.owner = owner; return true; } return false; }
/** {@inheritDoc} */ public void accept(Object owner, Object o) { // Look up the element wrapper record for the element to be accepted. RequeueElementWrapper<E> record = requeuedElementMap.get(o); if (record != null) { // If running in a transaction, create an accept operation to accept the item only upon commit // of the // transaction. if (transactional) { record.state = AcquireState.Accepted; txMethod.requestWriteOperation(new AcceptRecord(record)); } else { requeuedElementMap.remove(o); requeue.remove(record); } } }
/** {@inheritDoc} */ public boolean cancel(boolean mayInterruptIfRunning) { // release(TxManager.getTxIdFromThread(), record); record.state = AcquireState.Acquired; return true; }
/** {@inheritDoc} */ public E pollAccept(Object owner) { if (transactional) { E element = null; RequeueElementWrapper<E> record = null; // Find an element on the requeue that is free, or has already been acquired by the owner but // not accepted. // Mark the element as acquired by the owner as necessary. if (!requeue.isEmpty()) { for (RequeueElementWrapper<E> nextRecord : requeue) { if (AcquireState.Free.equals(nextRecord.state)) { record = nextRecord; record.state = AcquireState.Acquired; record.owner = owner; element = record.element; break; } else if (AcquireState.Acquired.equals(nextRecord.state) && owner.equals(nextRecord.owner)) { record = nextRecord; element = record.element; break; } } } // If an element cannot be found on the requeue, poll an element from the main queue, and // place it onto the // requeue. if (record == null) { element = queue.poll(); } // If no element at all can be found return null. if (element == null) { return element; } // Check that an element was actually available on the queue before creating a new acquired // record for it // on the requeue. if (record == null) { record = requeue(element, owner, AcquireState.Acquired); } // Accept the element and create a transaction operation to remove it upon commit or unnaccept // it upon // rollback. record.state = AcquireState.Accepted; txMethod.requestWriteOperation(new AcceptRecord(record)); return record.element; } else { E element; // Find an element on the requeue that is free. Remove it and return it. if (!requeue.isEmpty()) { for (RequeueElementWrapper<E> nextRecord : requeue) { if (AcquireState.Free.equals(nextRecord.state)) { requeue.remove(nextRecord); requeuedElementMap.remove(nextRecord.element); return nextRecord.element; } } } // Or poll an element from the main queue and return it. element = queue.poll(); if (element != null) { decrementSizeAndCount(element); } return element; } }