/** * @param message * @return */ private static RpcResponseKey createRpcResponseKey(final OfHeader message) { return new RpcResponseKey(message.getXid(), message.getImplementedInterface().getName()); }
private static boolean completeEntry(final OutboundQueueEntry entry, final OfHeader response) { if (response instanceof Error) { final Error err = (Error)response; LOG.debug("Device-reported request XID {} failed {}:{}", response.getXid(), err.getTypeString(), err.getCodeString()); entry.fail(new DeviceRequestFailedException("Device-side failure", err)); return true; } return entry.complete(response); }
/** * sends given message to switch, sending result or switch response will be reported via return value * * @param input message to send * @param responseClazz type of response * @param failureInfo describes, what type of message caused failure by sending * @return future object, * <ul> * <li>if send fails, {@link RpcResult} will contain errors and failed status</li> * <li>else {@link RpcResult} will be stored in responseCache and wait for particular timeout ( * {@link ConnectionAdapterImpl#RPC_RESPONSE_EXPIRATION}), * <ul> * <li>either switch will manage to answer and then corresponding response message will be set into returned * future</li> * <li>or response in cache will expire and returned future will be cancelled</li> * </ul> * </li> * </ul> */ protected <IN extends OfHeader, OUT extends OfHeader> ListenableFuture<RpcResult<OUT>> sendToSwitchExpectRpcResultFuture( final IN input, final Class<OUT> responseClazz, final String failureInfo) { final RpcResponseKey key = new RpcResponseKey(input.getXid(), responseClazz.getName()); final ResponseExpectedRpcListener<OUT> listener = new ResponseExpectedRpcListener<>(input, failureInfo, responseCache, key); return enqueueMessage(listener); }
OutboundQueueEntry pairRequest(final OfHeader response) { // Explicitly 'long' to force unboxing before performing operations final long xid = response.getXid(); if (!xidInRange(xid)) { LOG.debug("Queue {} {}/{} ignoring XID {}", this, baseXid, entries.length, xid); return null; } final int offset = (int) (xid - baseXid); final OutboundQueueEntry entry = entries[offset]; if (entry.isCompleted()) { LOG.debug("Entry {} already is completed, not accepting response {}", entry, response); return null; } if (entry.isBarrier()) { // This has been a barrier -- make sure we complete all preceding requests. // XXX: Barriers are expected to complete in one message. // If this assumption is changed, this logic will need to be expanded // to ensure that the requests implied by the barrier are reported as // completed *after* the barrier. LOG.trace("Barrier XID {} completed, cascading completion to XIDs {} to {}", xid, baseXid + lastBarrierOffset + 1, xid - 1); completeRequests(offset); lastBarrierOffset = offset; final boolean success = completeEntry(entry, response); Verify.verify(success, "Barrier request failed to complete"); completeCount++; } else if (completeEntry(entry, response)) { completeCount++; } return entry; }