|
Lines 49-54
Link Here
|
| 49 |
import org.omg.PortableServer.Servant; |
49 |
import org.omg.PortableServer.Servant; |
| 50 |
import org.omg.PortableServer.ServantActivator; |
50 |
import org.omg.PortableServer.ServantActivator; |
| 51 |
|
51 |
|
|
|
52 |
import edu.emory.mathcs.backport.java.util.concurrent.Callable; |
| 53 |
import edu.emory.mathcs.backport.java.util.concurrent.ExecutionException; |
| 54 |
import edu.emory.mathcs.backport.java.util.concurrent.Executor; |
| 55 |
import edu.emory.mathcs.backport.java.util.concurrent.FutureTask; |
| 56 |
import edu.emory.mathcs.backport.java.util.concurrent.TimeUnit; |
| 57 |
import edu.emory.mathcs.backport.java.util.concurrent.TimeoutException; |
| 58 |
import edu.emory.mathcs.backport.java.util.concurrent.locks.Condition; |
| 59 |
import edu.emory.mathcs.backport.java.util.concurrent.locks.Lock; |
| 60 |
import edu.emory.mathcs.backport.java.util.concurrent.locks.ReentrantLock; |
| 61 |
|
| 52 |
/** |
62 |
/** |
| 53 |
* JacORB implementation of CORBA object reference |
63 |
* JacORB implementation of CORBA object reference |
| 54 |
* |
64 |
* |
|
Lines 91-97
Link Here
|
| 91 |
private final Set pending_replies = new HashSet(); |
101 |
private final Set pending_replies = new HashSet(); |
| 92 |
private final Barrier pending_replies_sync = new Barrier(); |
102 |
private final Barrier pending_replies_sync = new Barrier(); |
| 93 |
|
103 |
|
| 94 |
private final java.lang.Object bind_sync = new java.lang.Object(); |
104 |
private final Lock bind_sync = new ReentrantLock(); |
|
|
105 |
private final Condition isConnected = bind_sync.newCondition(); |
| 95 |
|
106 |
|
| 96 |
private boolean locate_on_bind_performed = false; |
107 |
private boolean locate_on_bind_performed = false; |
| 97 |
|
108 |
|
|
Lines 119-125
Link Here
|
| 119 |
private boolean useIMR; |
130 |
private boolean useIMR; |
| 120 |
private boolean locateOnBind; |
131 |
private boolean locateOnBind; |
| 121 |
|
132 |
|
| 122 |
/** |
133 |
ThreadPerTaskExecutor executor = null; |
|
|
134 |
|
| 135 |
/** |
| 123 |
* 03-09-04: 1.5.2.2 |
136 |
* 03-09-04: 1.5.2.2 |
| 124 |
* |
137 |
* |
| 125 |
* boolean threadlocal to ensure that |
138 |
* boolean threadlocal to ensure that |
|
Lines 159-164
Link Here
|
| 159 |
super(); |
172 |
super(); |
| 160 |
|
173 |
|
| 161 |
this.orb = orb; |
174 |
this.orb = orb; |
|
|
175 |
this.executor = new ThreadPerTaskExecutor(); |
| 162 |
} |
176 |
} |
| 163 |
|
177 |
|
| 164 |
public Delegate ( org.jacorb.orb.ORB orb, ParsedIOR pior ) |
178 |
public Delegate ( org.jacorb.orb.ORB orb, ParsedIOR pior ) |
|
Lines 284-290
Link Here
|
| 284 |
*/ |
298 |
*/ |
| 285 |
private void bind(boolean rebind) |
299 |
private void bind(boolean rebind) |
| 286 |
{ |
300 |
{ |
| 287 |
synchronized (bind_sync) |
301 |
bind_sync.lock(); |
|
|
302 |
|
| 303 |
try |
| 288 |
{ |
304 |
{ |
| 289 |
if ( bound ) |
305 |
if ( bound ) |
| 290 |
{ |
306 |
{ |
|
Lines 351-356
Link Here
|
| 351 |
|
367 |
|
| 352 |
case LocateStatusType_1_2._OBJECT_HERE : |
368 |
case LocateStatusType_1_2._OBJECT_HERE : |
| 353 |
{ |
369 |
{ |
|
|
370 |
isConnected.signalAll(); |
| 354 |
break; |
371 |
break; |
| 355 |
} |
372 |
} |
| 356 |
|
373 |
|
|
Lines 403-411
Link Here
|
| 403 |
} |
420 |
} |
| 404 |
|
421 |
|
| 405 |
} |
422 |
} |
| 406 |
|
423 |
|
|
|
424 |
} |
| 425 |
finally |
| 426 |
{ |
| 407 |
//wake up threads waiting for the pior |
427 |
//wake up threads waiting for the pior |
| 408 |
bind_sync.notifyAll(); |
428 |
bind_sync.unlock(); |
| 409 |
} |
429 |
} |
| 410 |
} |
430 |
} |
| 411 |
|
431 |
|
|
Lines 425-431
Link Here
|
| 425 |
|
445 |
|
| 426 |
public void rebind(ParsedIOR ior) |
446 |
public void rebind(ParsedIOR ior) |
| 427 |
{ |
447 |
{ |
| 428 |
synchronized ( bind_sync ) |
448 |
bind_sync.lock(); |
|
|
449 |
try |
| 429 |
{ |
450 |
{ |
| 430 |
// Do the ParsedIORs currently match. |
451 |
// Do the ParsedIORs currently match. |
| 431 |
final ParsedIOR originalIOR = getParsedIOR(); |
452 |
final ParsedIOR originalIOR = getParsedIOR(); |
|
Lines 474-479
Link Here
|
| 474 |
|
495 |
|
| 475 |
bind(); |
496 |
bind(); |
| 476 |
} |
497 |
} |
|
|
498 |
finally |
| 499 |
{ |
| 500 |
bind_sync.unlock(); |
| 501 |
} |
| 477 |
} |
502 |
} |
| 478 |
|
503 |
|
| 479 |
public org.omg.CORBA.Request create_request( org.omg.CORBA.Object self, |
504 |
public org.omg.CORBA.Request create_request( org.omg.CORBA.Object self, |
|
Lines 792-807
Link Here
|
| 792 |
|
817 |
|
| 793 |
ClientConnection getConnection() |
818 |
ClientConnection getConnection() |
| 794 |
{ |
819 |
{ |
| 795 |
synchronized ( bind_sync ) |
820 |
bind_sync.lock(); |
|
|
821 |
try |
| 796 |
{ |
822 |
{ |
| 797 |
bind(); |
823 |
bind(); |
| 798 |
return connection; |
824 |
return connection; |
| 799 |
} |
825 |
} |
|
|
826 |
finally |
| 827 |
{ |
| 828 |
bind_sync.unlock(); |
| 829 |
} |
| 800 |
} |
830 |
} |
| 801 |
|
831 |
|
| 802 |
public org.omg.IOP.IOR getIOR() |
832 |
public org.omg.IOP.IOR getIOR() |
| 803 |
{ |
833 |
{ |
| 804 |
synchronized ( bind_sync ) |
834 |
bind_sync.lock(); |
|
|
835 |
|
| 836 |
try |
| 805 |
{ |
837 |
{ |
| 806 |
if ( piorOriginal != null ) |
838 |
if ( piorOriginal != null ) |
| 807 |
{ |
839 |
{ |
|
Lines 809-845
Link Here
|
| 809 |
} |
841 |
} |
| 810 |
return getParsedIOR().getIOR(); |
842 |
return getParsedIOR().getIOR(); |
| 811 |
} |
843 |
} |
|
|
844 |
finally |
| 845 |
{ |
| 846 |
bind_sync.unlock(); |
| 847 |
} |
| 812 |
} |
848 |
} |
| 813 |
|
849 |
|
| 814 |
public byte[] getObjectId() |
850 |
public byte[] getObjectId() |
| 815 |
{ |
851 |
{ |
| 816 |
synchronized ( bind_sync ) |
852 |
bind_sync.lock(); |
|
|
853 |
try |
| 817 |
{ |
854 |
{ |
| 818 |
bind(); |
855 |
bind(); |
| 819 |
|
856 |
|
| 820 |
return POAUtil.extractOID( getParsedIOR().get_object_key() ); |
857 |
return POAUtil.extractOID( getParsedIOR().get_object_key() ); |
| 821 |
} |
858 |
} |
|
|
859 |
finally |
| 860 |
{ |
| 861 |
bind_sync.unlock(); |
| 862 |
} |
| 822 |
} |
863 |
} |
| 823 |
|
864 |
|
| 824 |
public byte[] getObjectKey() |
865 |
public byte[] getObjectKey() |
| 825 |
{ |
866 |
{ |
| 826 |
synchronized ( bind_sync ) |
867 |
bind_sync.lock(); |
|
|
868 |
try |
| 827 |
{ |
869 |
{ |
| 828 |
bind(); |
870 |
bind(); |
| 829 |
|
871 |
|
| 830 |
return getParsedIOR().get_object_key(); |
872 |
return getParsedIOR().get_object_key(); |
| 831 |
} |
873 |
} |
|
|
874 |
finally |
| 875 |
{ |
| 876 |
bind_sync.unlock(); |
| 877 |
} |
| 832 |
} |
878 |
} |
| 833 |
|
879 |
|
| 834 |
public ParsedIOR getParsedIOR() |
880 |
public ParsedIOR getParsedIOR() |
| 835 |
{ |
881 |
{ |
| 836 |
synchronized ( bind_sync ) |
882 |
bind_sync.lock(); |
|
|
883 |
try |
| 837 |
{ |
884 |
{ |
| 838 |
while ( _pior == null ) |
885 |
while ( _pior == null ) |
| 839 |
{ |
886 |
{ |
| 840 |
try |
887 |
try |
| 841 |
{ |
888 |
{ |
| 842 |
bind_sync.wait(); |
889 |
isConnected.await(); |
| 843 |
} |
890 |
} |
| 844 |
catch ( InterruptedException ie ) |
891 |
catch ( InterruptedException ie ) |
| 845 |
{ |
892 |
{ |
|
Lines 849-854
Link Here
|
| 849 |
|
896 |
|
| 850 |
return _pior; |
897 |
return _pior; |
| 851 |
} |
898 |
} |
|
|
899 |
finally |
| 900 |
{ |
| 901 |
bind_sync.unlock(); |
| 902 |
} |
| 852 |
} |
903 |
} |
| 853 |
|
904 |
|
| 854 |
public void resolvePOA (org.omg.CORBA.Object self) |
905 |
public void resolvePOA (org.omg.CORBA.Object self) |
|
Lines 993-999
Link Here
|
| 993 |
interceptors.handle_send_request(); |
1044 |
interceptors.handle_send_request(); |
| 994 |
} |
1045 |
} |
| 995 |
|
1046 |
|
| 996 |
|
|
|
| 997 |
try |
1047 |
try |
| 998 |
{ |
1048 |
{ |
| 999 |
if ( !ros.response_expected() ) // oneway op |
1049 |
if ( !ros.response_expected() ) // oneway op |
|
Lines 1015-1038
Link Here
|
| 1015 |
pending_replies.add(receiver); |
1065 |
pending_replies.add(receiver); |
| 1016 |
} |
1066 |
} |
| 1017 |
|
1067 |
|
| 1018 |
synchronized (bind_sync) |
1068 |
// send the request by a background thread |
| 1019 |
{ |
1069 |
// |
| 1020 |
if (ros.getConnection() == connection) |
1070 |
|
| 1021 |
{ |
1071 |
SendJob sendJob = new SendJob(ros, receiver); |
| 1022 |
// RequestOutputStream has been created for |
1072 |
FutureTask task = new FutureTask(sendJob); |
| 1023 |
// exactly this connection |
1073 |
|
| 1024 |
connection.sendRequest(ros, receiver, ros.requestId(), true); // response |
1074 |
executor.execute(task); |
| 1025 |
// expected |
1075 |
|
| 1026 |
} |
1076 |
try |
| 1027 |
else |
1077 |
{ |
| 1028 |
{ |
1078 |
task.get(getTimeLeft(ros), TimeUnit.MILLISECONDS); |
| 1029 |
logger.debug("invoke: RemarshalException"); |
1079 |
} |
| 1030 |
|
1080 |
catch (InterruptedException e) |
| 1031 |
// RequestOutputStream has been created for |
1081 |
{ |
| 1032 |
// another connection, so try again |
1082 |
throw new TRANSIENT("interrupted while sending the request"); |
| 1033 |
throw new RemarshalException(); |
1083 |
} |
| 1034 |
} |
1084 |
catch (ExecutionException e) |
| 1035 |
} |
1085 |
{ |
|
|
1086 |
if(e.getCause() instanceof SystemException) |
| 1087 |
{ |
| 1088 |
throw (SystemException)e.getCause(); |
| 1089 |
} |
| 1090 |
else |
| 1091 |
{ |
| 1092 |
throw new RuntimeException(e); |
| 1093 |
} |
| 1094 |
} |
| 1095 |
catch (TimeoutException e) |
| 1096 |
{ |
| 1097 |
throw new TIMEOUT(e.getMessage()); |
| 1098 |
} |
| 1036 |
} |
1099 |
} |
| 1037 |
catch ( org.omg.CORBA.SystemException cfe ) |
1100 |
catch ( org.omg.CORBA.SystemException cfe ) |
| 1038 |
{ |
1101 |
{ |
|
Lines 1050-1056
Link Here
|
| 1050 |
} |
1113 |
} |
| 1051 |
|
1114 |
|
| 1052 |
interceptors.handle_receive_exception ( cfe ); |
1115 |
interceptors.handle_receive_exception ( cfe ); |
| 1053 |
|
1116 |
|
| 1054 |
// The exception is a TRANSIENT, so try rebinding. |
1117 |
// The exception is a TRANSIENT, so try rebinding. |
| 1055 |
if ( cfe instanceof org.omg.CORBA.TRANSIENT && try_rebind() ) |
1118 |
if ( cfe instanceof org.omg.CORBA.TRANSIENT && try_rebind() ) |
| 1056 |
{ |
1119 |
{ |
|
Lines 1058-1065
Link Here
|
| 1058 |
} |
1121 |
} |
| 1059 |
|
1122 |
|
| 1060 |
throw cfe; |
1123 |
throw cfe; |
| 1061 |
} |
1124 |
} |
| 1062 |
finally |
1125 |
finally |
| 1063 |
{ |
1126 |
{ |
| 1064 |
if (orb.hasRequestInterceptors()) |
1127 |
if (orb.hasRequestInterceptors()) |
| 1065 |
{ |
1128 |
{ |
|
Lines 1081-1086
Link Here
|
| 1081 |
return null; |
1144 |
return null; |
| 1082 |
} |
1145 |
} |
| 1083 |
|
1146 |
|
|
|
1147 |
private long getTimeLeft(RequestOutputStream ros2) |
| 1148 |
{ |
| 1149 |
UtcT timo = ros2.getReplyEndTime(); |
| 1150 |
long timoMillies = java.lang.Long.MAX_VALUE; |
| 1151 |
|
| 1152 |
if(timo != null) |
| 1153 |
{ |
| 1154 |
timoMillies = org.jacorb.util.Time.millisTo(timo); |
| 1155 |
} |
| 1156 |
return(timoMillies); |
| 1157 |
} |
| 1158 |
|
| 1159 |
public void doSend(RequestOutputStream ros, ReplyReceiver receiver) throws RemarshalException, InterruptedException |
| 1160 |
{ |
| 1161 |
long timo = getTimeLeft(ros); |
| 1162 |
|
| 1163 |
if( bind_sync.tryLock(timo, TimeUnit.MILLISECONDS) == false) |
| 1164 |
{ |
| 1165 |
throw new TIMEOUT("TIMO while doSend "); |
| 1166 |
} |
| 1167 |
|
| 1168 |
try |
| 1169 |
{ |
| 1170 |
if (ros.getConnection() == connection) |
| 1171 |
{ |
| 1172 |
// RequestOutputStream has been created for |
| 1173 |
// exactly this connection |
| 1174 |
connection.sendRequest(ros, receiver, ros.requestId(), true); // response |
| 1175 |
// expected |
| 1176 |
} |
| 1177 |
else |
| 1178 |
{ |
| 1179 |
logger.debug("invoke: RemarshalException"); |
| 1180 |
|
| 1181 |
// RequestOutputStream has been created for |
| 1182 |
// another connection, so try again |
| 1183 |
throw new RemarshalException(); |
| 1184 |
} |
| 1185 |
} |
| 1186 |
finally |
| 1187 |
{ |
| 1188 |
bind_sync.unlock(); |
| 1189 |
} |
| 1190 |
} |
| 1191 |
|
| 1084 |
private void invoke_oneway (RequestOutputStream ros, |
1192 |
private void invoke_oneway (RequestOutputStream ros, |
| 1085 |
ClientInterceptorHandler interceptors) |
1193 |
ClientInterceptorHandler interceptors) |
| 1086 |
throws RemarshalException, ApplicationException |
1194 |
throws RemarshalException, ApplicationException |
|
Lines 1132-1138
Link Here
|
| 1132 |
|
1240 |
|
| 1133 |
private boolean try_rebind() |
1241 |
private boolean try_rebind() |
| 1134 |
{ |
1242 |
{ |
| 1135 |
synchronized ( bind_sync ) |
1243 |
bind_sync.lock(); |
|
|
1244 |
try |
| 1136 |
{ |
1245 |
{ |
| 1137 |
if( logger.isDebugEnabled()) |
1246 |
if( logger.isDebugEnabled()) |
| 1138 |
{ |
1247 |
{ |
|
Lines 1227-1232
Link Here
|
| 1227 |
return false; |
1336 |
return false; |
| 1228 |
} |
1337 |
} |
| 1229 |
} |
1338 |
} |
|
|
1339 |
finally |
| 1340 |
{ |
| 1341 |
bind_sync.unlock(); |
| 1342 |
} |
| 1230 |
} |
1343 |
} |
| 1231 |
|
1344 |
|
| 1232 |
public void invokeInterceptors( ClientRequestInfoImpl info, short op ) |
1345 |
public void invokeInterceptors( ClientRequestInfoImpl info, short op ) |
|
Lines 1601-1607
Link Here
|
| 1601 |
*/ |
1714 |
*/ |
| 1602 |
public void release( org.omg.CORBA.Object self ) |
1715 |
public void release( org.omg.CORBA.Object self ) |
| 1603 |
{ |
1716 |
{ |
| 1604 |
synchronized ( bind_sync ) |
1717 |
bind_sync.lock(); |
|
|
1718 |
try |
| 1605 |
{ |
1719 |
{ |
| 1606 |
if (!bound) |
1720 |
if (!bound) |
| 1607 |
{ |
1721 |
{ |
|
Lines 1625-1630
Link Here
|
| 1625 |
logger.debug("Delegate released!"); |
1739 |
logger.debug("Delegate released!"); |
| 1626 |
} |
1740 |
} |
| 1627 |
} |
1741 |
} |
|
|
1742 |
finally |
| 1743 |
{ |
| 1744 |
bind_sync.unlock(); |
| 1745 |
} |
| 1628 |
} |
1746 |
} |
| 1629 |
|
1747 |
|
| 1630 |
/** |
1748 |
/** |
|
Lines 1652-1658
Link Here
|
| 1652 |
{ |
1770 |
{ |
| 1653 |
orb.perform_work(); |
1771 |
orb.perform_work(); |
| 1654 |
|
1772 |
|
| 1655 |
synchronized ( bind_sync ) |
1773 |
bind_sync.lock(); |
|
|
1774 |
try |
| 1656 |
{ |
1775 |
{ |
| 1657 |
bind(); |
1776 |
bind(); |
| 1658 |
return new org.jacorb.orb.dii.Request( self, |
1777 |
return new org.jacorb.orb.dii.Request( self, |
|
Lines 1661-1666
Link Here
|
| 1661 |
getParsedIOR().get_object_key(), |
1780 |
getParsedIOR().get_object_key(), |
| 1662 |
operation ); |
1781 |
operation ); |
| 1663 |
} |
1782 |
} |
|
|
1783 |
finally |
| 1784 |
{ |
| 1785 |
bind_sync.unlock(); |
| 1786 |
} |
| 1664 |
} |
1787 |
} |
| 1665 |
|
1788 |
|
| 1666 |
/** |
1789 |
/** |
|
Lines 1694-1712
Link Here
|
| 1694 |
|
1817 |
|
| 1695 |
UtcT replyEndTime = getReplyEndTime(); |
1818 |
UtcT replyEndTime = getReplyEndTime(); |
| 1696 |
long roundtripTimeout = getRelativeRoundtripTimeout(); |
1819 |
long roundtripTimeout = getRelativeRoundtripTimeout(); |
|
|
1820 |
long timo = Long.MAX_VALUE; |
| 1697 |
|
1821 |
|
| 1698 |
if ((roundtripTimeout != 0) || (replyEndTime != null)) |
1822 |
if ((roundtripTimeout != 0) || (replyEndTime != null)) |
| 1699 |
{ |
1823 |
{ |
| 1700 |
replyEndTime = Time.earliest(Time.corbaFuture (roundtripTimeout), |
1824 |
replyEndTime = Time.earliest(Time.corbaFuture (roundtripTimeout), |
| 1701 |
replyEndTime); |
1825 |
replyEndTime); |
|
|
1826 |
if(replyEndTime != null) |
| 1827 |
{ |
| 1828 |
timo = Time.millisTo(replyEndTime); |
| 1829 |
} |
| 1830 |
|
| 1702 |
if (Time.hasPassed(replyEndTime)) |
1831 |
if (Time.hasPassed(replyEndTime)) |
| 1703 |
{ |
1832 |
{ |
| 1704 |
throw new TIMEOUT("Reply End Time exceeded prior to invocation", |
1833 |
throw new TIMEOUT("Reply End Time exceeded prior to invocation", |
| 1705 |
0, CompletionStatus.COMPLETED_NO); |
1834 |
0, CompletionStatus.COMPLETED_NO); |
| 1706 |
} |
1835 |
} |
| 1707 |
} |
1836 |
} |
| 1708 |
|
1837 |
|
| 1709 |
synchronized ( bind_sync ) |
1838 |
try |
|
|
1839 |
{ |
| 1840 |
if( bind_sync.tryLock(timo, TimeUnit.MILLISECONDS) == false) |
| 1841 |
{ |
| 1842 |
throw new TIMEOUT("Reply End Time exceeded prior to invocation", |
| 1843 |
0, CompletionStatus.COMPLETED_NO); |
| 1844 |
} |
| 1845 |
} |
| 1846 |
catch (InterruptedException e) |
| 1847 |
{ |
| 1848 |
throw new TRANSIENT("interrupted while request generation"); |
| 1849 |
} |
| 1850 |
|
| 1851 |
try |
| 1710 |
{ |
1852 |
{ |
| 1711 |
bind(); |
1853 |
bind(); |
| 1712 |
|
1854 |
|
|
Lines 1744-1749
Link Here
|
| 1744 |
|
1886 |
|
| 1745 |
return out; |
1887 |
return out; |
| 1746 |
} |
1888 |
} |
|
|
1889 |
finally |
| 1890 |
{ |
| 1891 |
bind_sync.unlock(); |
| 1892 |
} |
| 1747 |
} |
1893 |
} |
| 1748 |
|
1894 |
|
| 1749 |
/** |
1895 |
/** |
|
Lines 1943-1949
Link Here
|
| 1943 |
|
2089 |
|
| 1944 |
public String toString() |
2090 |
public String toString() |
| 1945 |
{ |
2091 |
{ |
| 1946 |
synchronized ( bind_sync ) |
2092 |
bind_sync.lock(); |
|
|
2093 |
try |
| 1947 |
{ |
2094 |
{ |
| 1948 |
if ( piorOriginal != null ) |
2095 |
if ( piorOriginal != null ) |
| 1949 |
{ |
2096 |
{ |
|
Lines 1951-1956
Link Here
|
| 1951 |
} |
2098 |
} |
| 1952 |
return getParsedIOR().getIORString(); |
2099 |
return getParsedIOR().getIORString(); |
| 1953 |
} |
2100 |
} |
|
|
2101 |
finally |
| 2102 |
{ |
| 2103 |
bind_sync.unlock(); |
| 2104 |
} |
| 1954 |
} |
2105 |
} |
| 1955 |
|
2106 |
|
| 1956 |
public String toString( org.omg.CORBA.Object self ) |
2107 |
public String toString( org.omg.CORBA.Object self ) |
|
Lines 2057-2060
Link Here
|
| 2057 |
this.notifyAll(); |
2208 |
this.notifyAll(); |
| 2058 |
} |
2209 |
} |
| 2059 |
} |
2210 |
} |
|
|
2211 |
|
| 2212 |
private class ThreadPerTaskExecutor implements Executor |
| 2213 |
{ |
| 2214 |
ThreadGroup group; |
| 2215 |
|
| 2216 |
ThreadPerTaskExecutor() |
| 2217 |
{ |
| 2218 |
group = new ThreadGroup("Job Runner"); |
| 2219 |
group.setDaemon(true); |
| 2220 |
} |
| 2221 |
|
| 2222 |
public void execute(Runnable r) |
| 2223 |
{ |
| 2224 |
new Thread(group, r).start(); |
| 2225 |
} |
| 2226 |
} |
| 2227 |
|
| 2228 |
// a SendJob is a helper class used to send requests in background |
| 2229 |
// |
| 2230 |
private class SendJob implements Callable |
| 2231 |
{ |
| 2232 |
private RequestOutputStream ros; |
| 2233 |
private ReplyReceiver receiver; |
| 2234 |
|
| 2235 |
SendJob(RequestOutputStream ros, ReplyReceiver receiver) |
| 2236 |
{ |
| 2237 |
this.ros = ros; |
| 2238 |
this.receiver = receiver; |
| 2239 |
} |
| 2240 |
|
| 2241 |
public java.lang.Object call() throws Exception |
| 2242 |
{ |
| 2243 |
doSend(ros, receiver); |
| 2244 |
|
| 2245 |
return(null); |
| 2246 |
} |
| 2247 |
} |
| 2060 |
} |
2248 |
} |