Merge "Gracefully stop HT threads when the bundle is being stopped (cache terminated...
[controller.git] / opendaylight / forwardingrulesmanager / implementation / src / main / java / org / opendaylight / controller / forwardingrulesmanager / internal / FlowEntryDistributionOrderFutureTask.java
1 /*
2  * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
3  *
4  * This program and the accompanying materials are made available under the
5  * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6  * and is available at http://www.eclipse.org/legal/epl-v10.html
7  */
8
9 /**
10  * Class which will monitor the completion of a FlowEntryDistributionOrder it
11  * implements a Future interface so it can be inspected by who is waiting for
12  * it.
13  */
14 package org.opendaylight.controller.forwardingrulesmanager.internal;
15
16 import java.util.concurrent.CountDownLatch;
17 import java.util.concurrent.ExecutionException;
18 import java.util.concurrent.Future;
19 import java.util.concurrent.TimeUnit;
20 import java.util.concurrent.TimeoutException;
21
22 import org.opendaylight.controller.forwardingrulesmanager.implementation.data.FlowEntryDistributionOrder;
23 import org.opendaylight.controller.sal.utils.Status;
24 import org.opendaylight.controller.sal.utils.StatusCode;
25
26 /**
27  * Class which will monitor the completion of a FlowEntryDistributionOrder it
28  * implements a Future interface so it can be inspected by who is waiting for
29  * it.
30  */
31 final class FlowEntryDistributionOrderFutureTask implements Future<Status> {
32     private final FlowEntryDistributionOrder order;
33     private boolean amICancelled;
34     private CountDownLatch waitingLatch;
35     private Status retStatus;
36
37     /**
38      * @param order
39      *            for which we are monitoring the execution
40      */
41     FlowEntryDistributionOrderFutureTask(FlowEntryDistributionOrder order) {
42         // Order being monitored
43         this.order = order;
44         this.amICancelled = false;
45         // We need to wait for one completion to happen
46         this.waitingLatch = new CountDownLatch(1);
47         // No return status yet!
48         this.retStatus = new Status(StatusCode.UNDEFINED);
49     }
50
51     @Override
52     public boolean cancel(boolean mayInterruptIfRunning) {
53         return false;
54     }
55
56     @Override
57     public Status get() throws InterruptedException, ExecutionException {
58         // If i'm done lets return the status as many times as caller wants
59         if (this.waitingLatch.getCount() == 0L) {
60             return retStatus;
61         }
62
63         // Wait till someone signal that we are done
64         this.waitingLatch.await();
65
66         // Return the known status
67         return retStatus;
68     }
69
70     @Override
71     public Status get(long timeout, TimeUnit unit) throws InterruptedException,
72             ExecutionException, TimeoutException {
73         // If i'm done lets return the status as many times as caller wants
74         if (this.waitingLatch.getCount() == 0L) {
75             return retStatus;
76         }
77
78         // Wait till someone signal that we are done
79         this.waitingLatch.await(timeout, unit);
80
81         // Return the known status, could also be null if didn't return
82         return retStatus;
83     }
84
85     @Override
86     public boolean isCancelled() {
87         return this.amICancelled;
88     }
89
90     @Override
91     public boolean isDone() {
92         return (this.waitingLatch.getCount() == 0L);
93     }
94
95     /**
96      * Used by the thread that gets back the status for the order so can unblock
97      * an eventual caller waiting on the result to comes back
98      *
99      * @param order
100      * @param retStatus
101      */
102     void gotStatus(FlowEntryDistributionOrder order, Status retStatus) {
103         if (order != this.order) {
104             // Weird we got a call for an order we didn't make
105             return;
106         }
107         this.retStatus = retStatus;
108         // Now we are not waiting any longer
109         this.waitingLatch.countDown();
110     }
111 }