summaryrefslogtreecommitdiff
path: root/java/src/IceInternal/OutgoingAsyncBase.java
diff options
context:
space:
mode:
authorMatthew Newhook <matthew@zeroc.com>2014-09-27 16:31:46 -0700
committerMatthew Newhook <matthew@zeroc.com>2014-09-27 16:32:21 -0700
commit4951bbabdd6bd33a8e9ca0cdd46aad613a634626 (patch)
tree8634b14a258d2c9cee0e17a12af805e1af3fec76 /java/src/IceInternal/OutgoingAsyncBase.java
parentFixed deadlock in connection binding code (ICE-5693) (diff)
downloadice-4951bbabdd6bd33a8e9ca0cdd46aad613a634626.tar.bz2
ice-4951bbabdd6bd33a8e9ca0cdd46aad613a634626.tar.xz
ice-4951bbabdd6bd33a8e9ca0cdd46aad613a634626.zip
- begin_ now never interrupts.
- All potentially blocking Ice APIs are interruption points. - Fixes to the incoming/outgoing factories and shutdown procedure - Fixed bug where connect() was from a user thread. - Added lots more tests to the interrupt test suite.
Diffstat (limited to 'java/src/IceInternal/OutgoingAsyncBase.java')
-rw-r--r--java/src/IceInternal/OutgoingAsyncBase.java75
1 files changed, 46 insertions, 29 deletions
diff --git a/java/src/IceInternal/OutgoingAsyncBase.java b/java/src/IceInternal/OutgoingAsyncBase.java
index 8be0b3072bd..1497e45460e 100644
--- a/java/src/IceInternal/OutgoingAsyncBase.java
+++ b/java/src/IceInternal/OutgoingAsyncBase.java
@@ -21,7 +21,7 @@ import Ice.UserException;
* With this object, an application can obtain several attributes of the
* invocation and discover its outcome.
**/
-public class OutgoingAsyncBase implements Ice.AsyncResult
+public abstract class OutgoingAsyncBase implements Ice.AsyncResult
{
protected OutgoingAsyncBase(Communicator communicator, IceInternal.Instance instance, String op,
IceInternal.CallbackBase del)
@@ -106,6 +106,10 @@ public class OutgoingAsyncBase implements Ice.AsyncResult
{
synchronized(_monitor)
{
+ if(Thread.interrupted())
+ {
+ throw new Ice.OperationInterruptedException();
+ }
while((_state & StateDone) == 0)
{
try
@@ -148,6 +152,10 @@ public class OutgoingAsyncBase implements Ice.AsyncResult
{
synchronized(_monitor)
{
+ if(Thread.interrupted())
+ {
+ throw new Ice.OperationInterruptedException();
+ }
while((_state & StateSent) == 0 && _exception == null)
{
try
@@ -235,36 +243,44 @@ public class OutgoingAsyncBase implements Ice.AsyncResult
public final boolean __wait()
{
- synchronized(_monitor)
+ try
{
- if((_state & StateEndCalled) > 0)
- {
- throw new java.lang.IllegalArgumentException("end_ method called more than once");
- }
- _state |= StateEndCalled;
- while((_state & StateDone) == 0)
+ synchronized(_monitor)
{
- try
+ if((_state & StateEndCalled) > 0)
+ {
+ throw new java.lang.IllegalArgumentException("end_ method called more than once");
+ }
+
+ _state |= StateEndCalled;
+ if(Thread.interrupted())
+ {
+ throw new InterruptedException();
+ }
+ while((_state & StateDone) == 0)
{
_monitor.wait();
}
- catch(InterruptedException ex)
+
+ if(_exception != null)
{
- //
- // Remove the EndCalled flag since it should be possible to
- // call end_* again on the AsyncResult.
- //
- _state &= ~StateEndCalled;
- throw new Ice.OperationInterruptedException();
+ //throw (LocalException)_exception.fillInStackTrace();
+ throw _exception;
}
+
+ return (_state & StateOK) > 0;
}
- if(_exception != null)
- {
- //throw (LocalException)_exception.fillInStackTrace();
- throw _exception;
- }
- return (_state & StateOK) > 0;
}
+ catch(InterruptedException ex)
+ {
+ // This must be called outside of the monitor as the
+ // invocation will potentially want to lock the
+ // connection (which in turn may want to lock the outgoing
+ // to notify that the message has been sent).
+ cancelRequest();
+ throw new Ice.OperationInterruptedException();
+ }
+
}
public final void throwUserException()
@@ -405,14 +421,13 @@ public class OutgoingAsyncBase implements Ice.AsyncResult
try
{
_instance.clientThreadPool().dispatch(new IceInternal.DispatchWorkItem(_cachedConnection)
+ {
+ @Override
+ public void run()
{
- @Override
- public void
- run()
- {
- invokeSentInternal();
- }
- });
+ invokeSentInternal();
+ }
+ });
}
catch(CommunicatorDestroyedException exc)
{
@@ -548,6 +563,8 @@ public class OutgoingAsyncBase implements Ice.AsyncResult
String s = "error raised by AMI callback:\n" + IceInternal.Ex.toString(error);
_instance.initializationData().logger.error(s);
}
+
+ abstract protected void cancelRequest();
protected Communicator _communicator;
protected IceInternal.Instance _instance;