From: <mar...@us...> - 2013-12-09 08:18:28
|
Revision: 7614 http://bigdata.svn.sourceforge.net/bigdata/?rev=7614&view=rev Author: martyncutcher Date: 2013-12-09 08:18:21 +0000 (Mon, 09 Dec 2013) Log Message: ----------- Add service specific methods for doPipelineRemove/doWithdrawVote.. etc to allow the forcing of zookeeper state changes by "controlling" services, where previously global zookeeper state changes were only triggered by the effected service. This has been introduced specifically to support the forced removal of a service as a result of a sudden death or wire pull. Modified Paths: -------------- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/AbstractQuorum.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/QuorumActor.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/quorum/MockQuorumFixture.java branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/quorum/zk/ZKQuorumImpl.java Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/AbstractQuorum.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/AbstractQuorum.java 2013-12-09 08:13:26 UTC (rev 7613) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/AbstractQuorum.java 2013-12-09 08:18:21 UTC (rev 7614) @@ -2289,16 +2289,36 @@ abstract protected void doMemberAdd(); - abstract protected void doMemberRemove(); + final protected void doMemberRemove() { + doMemberRemove(serviceId); + } + abstract protected void doMemberRemove(UUID serviceId); + abstract protected void doCastVote(long lastCommitTime); - abstract protected void doWithdrawVote(); + final protected void doWithdrawVote() { + doWithdrawVote(serviceId); + } + abstract protected void doWithdrawVote(UUID serviceId); + abstract protected void doPipelineAdd(); - abstract protected void doPipelineRemove(); + final protected void doPipelineRemove() { + doPipelineRemove(serviceId); + } + abstract protected void doPipelineRemove(UUID serviceId); + + @Override + public void forceRemoveService(final UUID psid) { + doMemberRemove(psid); + doWithdrawVote(psid); + doPipelineRemove(psid); + doServiceLeave(psid); + } + /** * Invoked when our client will become the leader to (a) reorganize the * write pipeline such that our client is the first service in the write @@ -2396,8 +2416,12 @@ abstract protected void doServiceJoin(); - abstract protected void doServiceLeave(); + final protected void doServiceLeave() { + doServiceLeave(serviceId); + } + abstract protected void doServiceLeave(UUID serviceId); + abstract protected void doSetToken(long newToken); // abstract protected void doSetLastValidToken(long newToken); Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/QuorumActor.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/QuorumActor.java 2013-12-09 08:13:26 UTC (rev 7613) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/QuorumActor.java 2013-12-09 08:18:21 UTC (rev 7614) @@ -205,4 +205,21 @@ */ void clearToken(); + /** + * Remove the service from the quorum. This should be called when a problem + * with the service is reported to the quorum leader, for example as a + * result of a failed RMI request or failed socket level write replication. + * Such errors arise either from network connectivity or service death. + * These problems will generally be cured, but the heatbeat timeout to cure + * the problem can cause write replication to block. This method may be used + * to force the timely reordering of the pipeline in order to work around + * the replication problem. This is not a permenant disabling of the service + * - the service may be restarted or may recover and reenter the quorum at + * any time. + * + * @param serviceId + * The UUID of the service to be removed. + */ + public void forceRemoveService(UUID serviceId); + } Modified: branches/MGC_1_3_0/bigdata/src/test/com/bigdata/quorum/MockQuorumFixture.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/test/com/bigdata/quorum/MockQuorumFixture.java 2013-12-09 08:13:26 UTC (rev 7613) +++ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/quorum/MockQuorumFixture.java 2013-12-09 08:18:21 UTC (rev 7614) @@ -846,32 +846,20 @@ fixture.memberAdd(serviceId); } - protected void doMemberRemove() { - fixture.memberRemove(serviceId); - } - protected void doCastVote(final long lastCommitTime) { fixture.castVote(serviceId, lastCommitTime); } - protected void doWithdrawVote() { - fixture.withdrawVote(serviceId); - } - protected void doPipelineAdd() { fixture.pipelineAdd(serviceId); } - protected void doPipelineRemove() { - fixture.pipelineRemove(serviceId); - } - protected void doServiceJoin() { fixture.serviceJoin(serviceId); } - protected void doServiceLeave() { - fixture.serviceLeave(serviceId); + protected void doServiceLeave(final UUID service) { + fixture.serviceLeave(service); } protected void doSetToken(final long newToken) { @@ -890,6 +878,21 @@ fixture.clearToken(); } + @Override + protected void doMemberRemove(UUID service) { + fixture.memberRemove(service); + } + + @Override + protected void doWithdrawVote(UUID service) { + fixture.withdrawVote(service); + } + + @Override + protected void doPipelineRemove(UUID service) { + fixture.pipelineRemove(service); + } + // /** // * {@inheritDoc} // * <p> Modified: branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/quorum/zk/ZKQuorumImpl.java =================================================================== --- branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/quorum/zk/ZKQuorumImpl.java 2013-12-09 08:13:26 UTC (rev 7613) +++ branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/quorum/zk/ZKQuorumImpl.java 2013-12-09 08:18:21 UTC (rev 7614) @@ -327,7 +327,7 @@ } @Override - protected void doMemberRemove() { + protected void doMemberRemove(final UUID service) { // get a valid zookeeper connection object. final ZooKeeper zk; try { @@ -340,7 +340,7 @@ try { zk.delete(logicalServiceId + "/" + QUORUM + "/" + QUORUM_MEMBER + "/" + QUORUM_MEMBER_PREFIX - + serviceIdStr, -1/* anyVersion */); + + service.toString(), -1/* anyVersion */); } catch (NoNodeException e) { // ignore. } catch (KeeperException e) { @@ -414,7 +414,7 @@ } @Override - protected void doPipelineRemove() { + protected void doPipelineRemove(final UUID service) { // get a valid zookeeper connection object. final ZooKeeper zk; try { @@ -446,7 +446,7 @@ } final QuorumServiceState state = (QuorumServiceState) SerializerUtil .deserialize(b); - if (serviceId.equals(state.serviceUUID())) { + if (service.equals(state.serviceUUID())) { zk.delete(zpath + "/" + s, -1/* anyVersion */); return; } @@ -636,7 +636,7 @@ * handles a concurrent delete by a simple retry loop. */ @Override - protected void doWithdrawVote() { + protected void doWithdrawVote(final UUID service) { // zpath for votes. final String votesZPath = getVotesZPath(); if (log.isInfoEnabled()) @@ -724,7 +724,7 @@ Thread.currentThread().interrupt(); return; } - if (serviceId.equals(state.serviceUUID())) { + if (service.equals(state.serviceUUID())) { // found our vote. try { // delete our vote. @@ -761,7 +761,7 @@ } // done. if (log.isInfoEnabled()) - log.info("withdrawn: serviceId=" + serviceIdStr + log.info("withdrawn: serviceId=" + service.toString() + ", lastCommitTime=" + lastCommitTime); return; } catch (NoNodeException e) { @@ -836,7 +836,7 @@ } @Override - protected void doServiceLeave() { + protected void doServiceLeave(final UUID service) { // get a valid zookeeper connection object. final ZooKeeper zk; try { @@ -871,7 +871,7 @@ } final QuorumServiceState state = (QuorumServiceState) SerializerUtil .deserialize(b); - if (serviceId.equals(state.serviceUUID())) { + if (service.equals(state.serviceUUID())) { // Found this service. zk.delete(zpath + "/" + s, -1/* anyVersion */); return; This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |
From: <tho...@us...> - 2013-12-09 15:11:05
|
Revision: 7618 http://bigdata.svn.sourceforge.net/bigdata/?rev=7618&view=rev Author: thompsonbry Date: 2013-12-09 15:10:58 +0000 (Mon, 09 Dec 2013) Log Message: ----------- sync to martyn. Modified Paths: -------------- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/AbstractQuorum.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/QuorumActor.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/quorum/TestHA3QuorumSemantics.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/quorum/zk/TestZkHA3QuorumSemantics.java Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/AbstractQuorum.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/AbstractQuorum.java 2013-12-09 14:57:04 UTC (rev 7617) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/AbstractQuorum.java 2013-12-09 15:10:58 UTC (rev 7618) @@ -2311,12 +2311,55 @@ abstract protected void doPipelineRemove(UUID serviceId); + abstract protected void doServiceJoin(); + + final protected void doServiceLeave() { + doServiceLeave(serviceId); + } + + abstract protected void doServiceLeave(UUID serviceId); + + abstract protected void doSetToken(long newToken); + +// abstract protected void doSetLastValidToken(long newToken); +// +// abstract protected void doSetToken(); + + abstract protected void doClearToken(); + + + /** + * {@inheritDoc} + * <p> + * Note: This implements an unconditional remove of the specified + * service. It is intended to force a different service out of the + * pipeline. This code deliberately takes this action unconditionally + * and does NOT await the requested state change. + * <p> + * Note: This code could potentially cause the remote service to + * deadlock in one of the conditionalXXX() methods if it is concurrently + * attempting to execute quorum action on itself. If this problem is + * observed, we should add a timeout to the conditionalXXX() methods + * that will force them to fail rather than block forever. This will + * then force the service into an error state if its QuorumActor can not + * carry out the requested action within a specified timeout. + * + * @throws InterruptedException + */ @Override - public void forceRemoveService(final UUID psid) { - doMemberRemove(psid); - doWithdrawVote(psid); - doPipelineRemove(psid); - doServiceLeave(psid); + final public void forceRemoveService(final UUID psid) + throws InterruptedException { + lock.lockInterruptibly(); + try { + log.warn("Forcing remove of service" + ": thisService=" + + serviceId + ", otherServiceId=" + psid); + doMemberRemove(psid); + doWithdrawVote(psid); + doPipelineRemove(psid); + doServiceLeave(psid); + } finally { + lock.unlock(); + } } /** @@ -2414,22 +2457,6 @@ return modified; } - abstract protected void doServiceJoin(); - - final protected void doServiceLeave() { - doServiceLeave(serviceId); - } - - abstract protected void doServiceLeave(UUID serviceId); - - abstract protected void doSetToken(long newToken); - -// abstract protected void doSetLastValidToken(long newToken); -// -// abstract protected void doSetToken(); - - abstract protected void doClearToken(); - } /** Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/QuorumActor.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/QuorumActor.java 2013-12-09 14:57:04 UTC (rev 7617) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/QuorumActor.java 2013-12-09 15:10:58 UTC (rev 7618) @@ -219,7 +219,8 @@ * * @param serviceId * The UUID of the service to be removed. + * @throws InterruptedException */ - public void forceRemoveService(UUID serviceId); + public void forceRemoveService(UUID serviceId) throws InterruptedException; } Modified: branches/MGC_1_3_0/bigdata/src/test/com/bigdata/quorum/TestHA3QuorumSemantics.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/test/com/bigdata/quorum/TestHA3QuorumSemantics.java 2013-12-09 14:57:04 UTC (rev 7617) +++ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/quorum/TestHA3QuorumSemantics.java 2013-12-09 15:10:58 UTC (rev 7618) @@ -1340,6 +1340,7 @@ * Rejoin the service. */ actor1.memberAdd(); + fixture.awaitDeque(); actor1.pipelineAdd(); fixture.awaitDeque(); actor1.castVote(lastCommitTime); @@ -1680,6 +1681,7 @@ } } + /** * Unit tests for pipeline reorganization when the leader is elected. This * tests the automatic reorganization of the pipeline order where the Modified: branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/quorum/zk/TestZkHA3QuorumSemantics.java =================================================================== --- branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/quorum/zk/TestZkHA3QuorumSemantics.java 2013-12-09 14:57:04 UTC (rev 7617) +++ branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/quorum/zk/TestZkHA3QuorumSemantics.java 2013-12-09 15:10:58 UTC (rev 7618) @@ -1073,6 +1073,9 @@ } + /** + * Unit test of {@link QuorumActor#forceRemoveService(UUID)}. + */ public void test_serviceJoin3_simpleForceRemove() throws InterruptedException { final Quorum<?, ?> quorum0 = quorums[0]; This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |
From: <tho...@us...> - 2013-12-10 21:37:05
|
Revision: 7630 http://bigdata.svn.sourceforge.net/bigdata/?rev=7630&view=rev Author: thompsonbry Date: 2013-12-10 21:36:50 +0000 (Tue, 10 Dec 2013) Log Message: ----------- Sync to Martyn on #779. I have added a listener protocol for the incremental write replication and sufficient hooks that we can force the failure of the write replication protocol by intercepting it at some desired point between the receive and the replicate of bytes in a payload. I added a sure kill for A+B+C where B is killed during a large load when it has receive two chunks of data for the large load. This test passes. I did a similar test where C is killed. This test fails - it gets to the end of the test and then discovers that the LOAD failed. Modified Paths: -------------- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumServiceBase.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HAReceiveService.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HASendService.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/TestAll.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/io/writecache/TestWORMWriteCacheService.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/TestWORMStrategyNoCache.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/ha/HABranch.txt branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/journal/jini/ha/HAJournalServer.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/AbstractHA3JournalServerTestCase.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/HAJournalTest.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHA3JustKills.java Removed Paths: ------------- branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/ha/AbstractHAJournalTestCase.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/ha/TestAll.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/ha/TestHAWORMStrategy.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/ha/TestHAWritePipeline.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/ha/TestJournalHA.java Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java 2013-12-09 20:53:38 UTC (rev 7629) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java 2013-12-10 21:36:50 UTC (rev 7630) @@ -847,11 +847,20 @@ // Setup the receive service. receiveService = new HAReceiveService<HAMessageWrapper>(addrSelf, addrNext, new IHAReceiveCallback<HAMessageWrapper>() { + @Override public void callback(final HAMessageWrapper msg, final ByteBuffer data) throws Exception { // delegate handling of write cache blocks. handleReplicatedWrite(msg.req, msg.msg, data); } + @Override + public void incReceive(final HAMessageWrapper msg, + final int nreads, final int rdlen, + final int rem) throws Exception { + // delegate handling of incremental receive notify. + QuorumPipelineImpl.this.incReceive(msg.req, + msg.msg, nreads, rdlen, rem); + } }); // Start the receive service - will not return until service is // running @@ -2056,6 +2065,27 @@ final IHAWriteMessage msg, final ByteBuffer data) throws Exception; /** + * Notify that some payload bytes have been incrementally received for an + * {@link IHAMessage}. + * + * @param msg + * The message. + * @param nreads + * The number of reads performed against the upstream socket for + * this message. + * @param rdlen + * The number of bytes read from the socket in this read. + * @param rem + * The number of bytes remaining before the payload has been + * fully read. + * + * @throws Exception + */ + abstract protected void incReceive(final IHASyncRequest req, + final IHAWriteMessage msg, final int nreads, final int rdlen, + final int rem) throws Exception; + + /** * A utility class that bundles together the Internet address and port at which * the downstream service will accept and relay cache blocks for the write * pipeline and the remote interface which is used to communicate with that Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumServiceBase.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumServiceBase.java 2013-12-09 20:53:38 UTC (rev 7629) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumServiceBase.java 2013-12-10 21:36:50 UTC (rev 7630) @@ -109,6 +109,15 @@ } @Override + protected void incReceive(final IHASyncRequest req, + final IHAWriteMessage msg, final int nreads, + final int rdlen, final int rem) throws Exception { + + QuorumServiceBase.this.incReceive(req, msg, nreads, rdlen, rem); + + } + + @Override protected long getRetrySendTimeoutNanos() { return QuorumServiceBase.this.getRetrySendTimeoutNanos(); @@ -262,8 +271,31 @@ */ abstract protected void handleReplicatedWrite(IHASyncRequest req, IHAWriteMessage msg, ByteBuffer data) throws Exception; - + /** + * Core implementation of callback for monitoring progress of replicated + * writes. + * + * @param req + * The synchronization request (optional). When non- + * <code>null</code> the message and payload are historical data. + * When <code>null</code> they are live data. + * @param msg + * Metadata about a buffer containing data replicated to this + * node. + * @param rdlen + * The number of bytes read from the socket in this read. + * @param rem + * The number of bytes remaining before the payload has been + * fully read. + * + * @throws Exception + */ + abstract protected void incReceive(final IHASyncRequest req, + final IHAWriteMessage msg, final int nreads, final int rdlen, + final int rem) throws Exception; + + /** * {@inheritDoc} * <p> * Note: The default implementation is a NOP. Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HAReceiveService.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HAReceiveService.java 2013-12-09 20:53:38 UTC (rev 7629) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HAReceiveService.java 2013-12-10 21:36:50 UTC (rev 7630) @@ -52,6 +52,7 @@ import org.apache.log4j.Logger; import com.bigdata.ha.QuorumPipelineImpl; +import com.bigdata.ha.msg.IHAMessage; import com.bigdata.ha.msg.IHASyncRequest; import com.bigdata.ha.msg.IHAWriteMessage; import com.bigdata.ha.msg.IHAWriteMessageBase; @@ -1079,6 +1080,11 @@ rem -= rdlen; + if (callback != null) { + // notify of incremental read. + callback.incReceive(message, reads, rdlen, rem); + } + /* * Now forward the most recent transfer bytes downstream * @@ -1349,6 +1355,25 @@ */ void callback(M msg, ByteBuffer data) throws Exception; + /** + * Notify that some payload bytes have been incrementally received for + * an {@link IHAMessage}. This is invoked each time some data has been + * read from the upstream socket. + * + * @param msg + * The message. + * @param nreads + * The number of reads performed against the upstream socket + * for this message. + * @param rdlen + * The number of bytes read from the socket in this read. + * @param rem + * The number of bytes remaining before the payload has been + * fully read. + * + * @throws Exception + */ + void incReceive(M msg, int nreads, int rdlen, int rem) throws Exception; } /** Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HASendService.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HASendService.java 2013-12-09 20:53:38 UTC (rev 7629) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HASendService.java 2013-12-10 21:36:50 UTC (rev 7630) @@ -131,10 +131,30 @@ * @see #start(InetSocketAddress) */ public HASendService() { + + this(true/* blocking */); + + } + + /** + * Note: This constructor is not exposed yet. We need to figure out whether + * to allow the configuration of the socket options and how to support that. + * + * @param blocking + */ + private HASendService(final boolean blocking) { + + this.blocking = blocking; - } + } /** + * <code>true</code> iff the client socket will be setup in a blocking mode. + * This is the historical behavior until at least Dec 10, 2013. + */ + private final boolean blocking; + + /** * Extended to ensure that the private executor service is always * terminated. */ @@ -422,22 +442,29 @@ * * @throws IOException */ - static private SocketChannel openChannel(final InetSocketAddress addr) + private SocketChannel openChannel(final InetSocketAddress addr) throws IOException { final SocketChannel socketChannel = SocketChannel.open(); try { - socketChannel.configureBlocking(true); + socketChannel.configureBlocking(blocking); if (log.isTraceEnabled()) log.trace("Connecting to " + addr); - socketChannel.connect(addr); + if (!socketChannel.connect(addr)) { + while (!socketChannel.finishConnect()) { + try { + Thread.sleep(10/* millis */); + } catch (InterruptedException e) { + // Propagate interrupt. + Thread.currentThread().interrupt(); + } + } + } - socketChannel.finishConnect(); - } catch (IOException ex) { log.error(ex); @@ -520,7 +547,7 @@ * socket buffer exchange and the send() Future will report * success even through the application code on the receiver * could fail once it gets control back from select(). This - * twist can be a bit suprising. Therefore it is useful to + * twist can be a bit surprising. Therefore it is useful to * write tests with both small payloads (the data transfer * will succeed at the socket level even if the application * logic then fails the transfer) and for large payloads. Modified: branches/MGC_1_3_0/bigdata/src/test/com/bigdata/TestAll.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/test/com/bigdata/TestAll.java 2013-12-09 20:53:38 UTC (rev 7629) +++ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/TestAll.java 2013-12-10 21:36:50 UTC (rev 7630) @@ -108,7 +108,6 @@ suite.addTest(com.bigdata.io.writecache.TestAll.suite()); suite.addTest( com.bigdata.journal.TestAll.suite() ); suite.addTest( com.bigdata.rwstore.TestAll.suite() ); - suite.addTest( com.bigdata.journal.ha.TestAll.suite() ); suite.addTest( com.bigdata.resources.TestAll.suite() ); suite.addTest( com.bigdata.relation.TestAll.suite() ); suite.addTest( com.bigdata.bop.TestAll.suite() ); Modified: branches/MGC_1_3_0/bigdata/src/test/com/bigdata/io/writecache/TestWORMWriteCacheService.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/test/com/bigdata/io/writecache/TestWORMWriteCacheService.java 2013-12-09 20:53:38 UTC (rev 7629) +++ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/io/writecache/TestWORMWriteCacheService.java 2013-12-10 21:36:50 UTC (rev 7630) @@ -339,6 +339,13 @@ } @Override + protected void incReceive(final IHASyncRequest req, + final IHAWriteMessage msg, final int nreads, + final int rdlen, final int rem) throws Exception { + // NOP + } + + @Override public UUID getStoreUUID() { return MyMockQuorumMember.this.getStoreUUID(); } @@ -380,7 +387,7 @@ MyMockQuorumMember.this.purgeHALogs(token); } - + }); } Modified: branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/TestWORMStrategyNoCache.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/TestWORMStrategyNoCache.java 2013-12-09 20:53:38 UTC (rev 7629) +++ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/TestWORMStrategyNoCache.java 2013-12-10 21:36:50 UTC (rev 7630) @@ -35,7 +35,6 @@ import junit.framework.Test; import com.bigdata.io.DirectBufferPool; -import com.bigdata.journal.ha.TestHAWORMStrategy; import com.bigdata.rawstore.IRawStore; /** @@ -44,7 +43,7 @@ * to operation when caching is disabled. * <p> * Note: The HA journal requires that cache be enabled. However, the HA journal - * is tested by a different test suite. See {@link TestHAWORMStrategy}. + * is tested by a different test suite. * * @author <a href="mailto:tho...@us...">Bryan Thompson</a> * @version $Id$ Deleted: branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/ha/AbstractHAJournalTestCase.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/ha/AbstractHAJournalTestCase.java 2013-12-09 20:53:38 UTC (rev 7629) +++ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/ha/AbstractHAJournalTestCase.java 2013-12-10 21:36:50 UTC (rev 7630) @@ -1,626 +0,0 @@ -/** - -Copyright (C) SYSTAP, LLC 2006-2007. All rights reserved. - -Contact: - SYSTAP, LLC - 4501 Tower Road - Greensboro, NC 27410 - lic...@bi... - -This program is free software; you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation; version 2 of the License. - -This program is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. - -You should have received a copy of the GNU General Public License -along with this program; if not, write to the Free Software -Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA -*/ -/* - * Created on Oct 14, 2006 - */ - -package com.bigdata.journal.ha; - -import java.io.File; -import java.io.IOException; -import java.net.BindException; -import java.net.InetSocketAddress; -import java.net.ServerSocket; -import java.net.UnknownHostException; -import java.nio.ByteBuffer; -import java.rmi.Remote; -import java.util.Properties; -import java.util.UUID; -import java.util.concurrent.TimeUnit; -import java.util.concurrent.TimeoutException; - -import junit.framework.TestCase; - -import com.bigdata.LRUNexus; -import com.bigdata.ha.HAGlue; -import com.bigdata.ha.QuorumService; -import com.bigdata.ha.QuorumServiceBase; -import com.bigdata.ha.msg.IHASyncRequest; -import com.bigdata.ha.msg.IHAWriteMessage; -import com.bigdata.journal.AbstractJournal; -import com.bigdata.journal.AbstractJournalTestCase; -import com.bigdata.journal.IRootBlockView; -import com.bigdata.journal.Journal; -import com.bigdata.journal.Options; -import com.bigdata.journal.ProxyTestCase; -import com.bigdata.quorum.MockQuorumFixture; -import com.bigdata.quorum.Quorum; -import com.bigdata.quorum.QuorumActor; - -/** - * <p> - * Abstract harness for testing under a variety of configurations. In order to - * test a specific configuration, create a concrete instance of this class. The - * configuration can be described using a mixture of a <code>.properties</code> - * file of the same name as the test class and custom code. - * </p> - * <p> - * When debugging from an IDE, it is very helpful to be able to run a single - * test case. You can do this, but you MUST define the property - * <code>testClass</code> as the name test class that has the logic required - * to instantiate and configure an appropriate object manager instance for the - * test. - * </p> - */ -abstract public class AbstractHAJournalTestCase - extends AbstractJournalTestCase -{ - - // - // Constructors. - // - - public AbstractHAJournalTestCase() {} - - public AbstractHAJournalTestCase(String name) {super(name);} - - //************************************************************ - //************************************************************ - //************************************************************ - - /** - * The replication factor for the quorum. This is initialized in - * {@link #setUp(ProxyTestCase)} so you can override it. The default is - * <code>3</code>, which is a highly available quorum. - */ - protected int k; - - /** - * The replication count (#of journals) for the quorum. This is initialized - * in {@link #setUp(ProxyTestCase)} so you can override it. The default is - * <code>3</code>, which is the same as the default replication factor - * {@link #k}. - */ - protected int replicationCount; - /** - * The fixture provides a mock of the distributed quorum state machine. - */ - protected MockQuorumFixture fixture = null; - /** - * The logical service identifier. - */ - protected String logicalServiceId = null; - /** - * The {@link Journal}s which are the members of the logical service. - */ - private Journal[] stores = null; - - /** - * Invoked from {@link TestCase#setUp()} for each test in the suite. - */ - public void setUp(ProxyTestCase testCase) throws Exception { - - super.setUp(testCase); - -// if(log.isInfoEnabled()) -// log.info("\n\n================:BEGIN:" + testCase.getName() -// + ":BEGIN:===================="); - - fixture = new MockQuorumFixture(); -// fixture.start(); - logicalServiceId = "logicalService_" + getName(); - - k = 3; - - replicationCount = 3; - - } - - /** - * Invoked from {@link TestCase#tearDown()} for each test in the suite. - */ - public void tearDown(ProxyTestCase testCase) throws Exception { - - if (stores != null) { - for (Journal store : stores) { - if (store != null) { - store.destroy(); - } - } - } - - if(fixture!=null) { - fixture.terminate(); - fixture = null; - } - - logicalServiceId = null; - - super.tearDown(testCase); - - } - - /** - * Note: Due to the manner in which the {@link MockQuorumManager} is - * initialized, the elements in {@link #stores} will be <code>null</code> - * initially. This should be Ok as long as the test gets fully setup before - * you start making requests of the {@link QuorumManager} or the - * {@link Quorum}. - */ - @Override - protected Journal getStore(final Properties properties) { - - stores = new Journal[replicationCount]; - - for (int i = 0; i < replicationCount; i++) { - - stores[i] = newJournal(properties); - - } - - /* - * FIXME It appears that it is necessary to start the QuorumFixture and - * then each Quorum *BEFORE* any quorum member takes an action, e.g., - * by doing a memberAdd(). That is likely a flaw in the QuorumFixture - * or the Quorum code. - */ - fixture.start(); - - for (int i = 0; i < replicationCount; i++) { - final Quorum<HAGlue, QuorumService<HAGlue>> quorum = stores[i] - .getQuorum(); - final HAJournal jnl = (HAJournal) stores[i]; - final UUID serviceId = jnl.getUUID(); - quorum.start(newQuorumService(logicalServiceId, serviceId, - jnl.newHAGlue(serviceId), jnl)); - } - - for (int i = 0; i < replicationCount; i++) { - final Quorum<HAGlue, QuorumService<HAGlue>> quorum = stores[i] - .getQuorum(); - final HAJournal jnl = (HAJournal) stores[i]; - /* - * Tell the actor to try and join the quorum. It will join iff our - * current root block can form a simple majority with the other - * services in the quorum. - */ - final QuorumActor<?, ?> actor = quorum.getActor(); - try { - - actor.memberAdd(); - fixture.awaitDeque(); - - actor.pipelineAdd(); - fixture.awaitDeque(); - - actor.castVote(jnl.getLastCommitTime()); - fixture.awaitDeque(); - - } catch (InterruptedException ex) { - - throw new RuntimeException(ex); - - } - } - - /* - * Initialize the master first. The followers will get their root blocks - * from the master. - */ -// fixture.join(stores[0]); -// fixture.join(stores[1]); -// fixture.join(stores[2]); -// -// stores[1].takeRootBlocksFromLeader(); -// stores[2].takeRootBlocksFromLeader(); - - /* - * @todo we probably have to return the service which joined as the - * leader from getStore(). - */ - final Quorum<HAGlue, QuorumService<HAGlue>> q = stores[0].getQuorum(); - - try { - - final long token = q.awaitQuorum(1L,TimeUnit.SECONDS); - assertEquals(token, stores[1].getQuorum().awaitQuorum(1L,TimeUnit.SECONDS)); - assertEquals(token, stores[2].getQuorum().awaitQuorum(1L,TimeUnit.SECONDS)); - - q.getClient().assertLeader(token); - - assertEquals(k, q.getMembers().length); - - } catch (TimeoutException ex) { -for(int i=0; i<3; i++)log.error("quorum["+i+"]:"+(stores[i].getQuorum()).toString()); - throw new RuntimeException(ex); - - } catch (InterruptedException ex) { - - throw new RuntimeException(ex); - - } - - // return the master. - return stores[0]; - - } - - protected Journal newJournal(final Properties properties) { - - /* - * Initialize the HA components. - */ - - final Quorum<HAGlue, QuorumService<HAGlue>> quorum = newQuorum(); - - final HAJournal jnl = new HAJournal(properties, quorum); - -// /* -// * FIXME This probably should be a constant across the life cycle of the -// * service, in which case it needs to be elevated outside of this method -// * which is used both to open and re-open the journal. -// */ -// final UUID serviceId = UUID.randomUUID(); - - /* - * Set the client on the quorum. - * - * FIXME The client needs to manage the quorumToken and various other - * things. - */ -// quorum.start(newQuorumService(logicalServiceId, serviceId, jnl -// .newHAGlue(serviceId), jnl)); - -// // discard the current write set. -// abort(); -// -// // set the quorum object. -// this.quorum.set(quorum); -// -// // save off the current token (typically NO_QUORUM unless standalone). -// quorumToken = quorum.token(); - -// /* -// * Tell the actor to try and join the quorum. It will join iff our -// * current root block can form a simple majority with the other services -// * in the quorum. -// */ -// final QuorumActor<?, ?> actor = quorum.getActor(); -// try { -// -// actor.memberAdd(); -// fixture.awaitDeque(); -// -// actor.pipelineAdd(); -// fixture.awaitDeque(); -// -// actor.castVote(jnl.getLastCommitTime()); -// fixture.awaitDeque(); -// -// } catch (InterruptedException ex) { -// -// throw new RuntimeException(ex); -// -// } - - return jnl; - -// return new Journal(properties) { -// -// protected Quorum<HAGlue, QuorumService<HAGlue>> newQuorum() { -// -// return AbstractHAJournalTestCase.this.newQuorum(); -// -// }; -// -// }; - - } - - private static class HAJournal extends Journal { - - /** - * @param properties - */ - public HAJournal(Properties properties, - Quorum<HAGlue, QuorumService<HAGlue>> quorum) { - super(properties, quorum); - } - - /** - * {@inheritDoc} - * <p> - * Note: This uses a random port on the loopback address. - */ - @Override - public HAGlue newHAGlue(final UUID serviceId) { - - final InetSocketAddress writePipelineAddr; - try { - writePipelineAddr = new InetSocketAddress(getPort(0)); - } catch (UnknownHostException e) { - throw new RuntimeException(e); - } catch (IOException e) { - throw new RuntimeException(e); - } - - return new HAGlueService(serviceId, writePipelineAddr); - - } - - /** - * Return an unused port. - * - * @param suggestedPort - * The suggested port. - * - * @return The suggested port, unless it is zero or already in use, in which - * case an unused port is returned. - * - * @throws IOException - */ - static protected int getPort(int suggestedPort) throws IOException { - ServerSocket openSocket; - try { - openSocket = new ServerSocket(suggestedPort); - } catch (BindException ex) { - // the port is busy, so look for a random open port - openSocket = new ServerSocket(0); - } - final int port = openSocket.getLocalPort(); - openSocket.close(); - return port; - } - - /** - * Extended implementation supports RMI. - */ - protected class HAGlueService extends BasicHA { - - protected HAGlueService(final UUID serviceId, - final InetSocketAddress writePipelineAddr) { - - super(serviceId, writePipelineAddr); - - } - - } - - } - - protected Quorum<HAGlue, QuorumService<HAGlue>> newQuorum() { - - return new MockQuorumFixture.MockQuorum<HAGlue, QuorumService<HAGlue>>( - k, fixture); - - }; - - /** - * Factory for the {@link QuorumService} implementation. - * - * @param remoteServiceImpl - * The object that implements the {@link Remote} interfaces - * supporting HA operations. - */ - protected QuorumServiceBase<HAGlue, AbstractJournal> newQuorumService( - final String logicalServiceId, - final UUID serviceId, final HAGlue remoteServiceImpl, - final AbstractJournal store) { - - return new QuorumServiceBase<HAGlue, AbstractJournal>(logicalServiceId, - serviceId, remoteServiceImpl, store) { - - /** - * Only the local service implementation object can be resolved. - */ - @Override - public HAGlue getService(final UUID serviceId) { - - return (HAGlue) fixture.getService(serviceId); - - } - - /** - * FIXME handle replicated writes. Probably just dump it on the - * jnl's WriteCacheService. Or maybe wrap it back up using a - * WriteCache and let that lay it down onto the disk. - */ - @Override - protected void handleReplicatedWrite(IHASyncRequest req, - IHAWriteMessage msg, ByteBuffer data) throws Exception { - - -// new WriteCache() { -// -// @Override -// protected boolean writeOnChannel(ByteBuffer buf, long firstOffset, -// Map<Long, RecordMetadata> recordMap, long nanos) -// throws InterruptedException, TimeoutException, IOException { -// // TODO Auto-generated method stub -// return false; -// } -// }; - - throw new UnsupportedOperationException(); - } - - @Override - public void installRootBlocks(IRootBlockView rootBlock0, - final IRootBlockView rootBlock1) { - throw new UnsupportedOperationException(); - } - -// @Override -// public void didMeet(final long token, final long commitCounter, -// final boolean isLeader) { -// throw new UnsupportedOperationException(); -// } - - @Override - public File getServiceDir() { - throw new UnsupportedOperationException(); - } - - @Override - public int getPID() { - throw new UnsupportedOperationException(); - } - - @Override - public void enterErrorState() { - // TODO Auto-generated method stub - } - - @Override - public void discardWriteSet() { - // TODO Auto-generated method stub - } - - @Override - protected long getRetrySendTimeoutNanos() { - return TimeUnit.MILLISECONDS.toNanos(100); // 100ms by default - } - - }; - - } - - /** - * Re-open the same backing store. - * - * @param store - * the existing store. - * - * @return A new store. - * - * @exception Throwable - * if the existing store is closed or if the store can not be - * re-opened, e.g., from failure to obtain a file lock, etc. - */ - @Override - protected Journal reopenStore(final Journal store) { - - if (stores[0] != store) - throw new AssertionError(); - - for (int i = 0; i < stores.length; i++) { - - Journal aStore = stores[i]; - - if (LRUNexus.INSTANCE != null) { - /* - * Drop the record cache for this store on reopen. This makes it - * easier to find errors related to a difference in the bytes on - * the disk versus the bytes in the record cache. - */ - LRUNexus.INSTANCE.deleteCache(aStore.getUUID()); - } - - // close the store. - aStore.close(); - - if (!aStore.isStable()) { - - throw new UnsupportedOperationException( - "The backing store is not stable"); - - } - - // Note: clone to avoid modifying!!! - final Properties properties = (Properties) getProperties().clone(); - - // Turn this off now since we want to re-open the same store. - properties.setProperty(Options.CREATE_TEMP_FILE, "false"); - - // The backing file that we need to re-open. - final File file = aStore.getFile(); - - if (file == null) - throw new AssertionError(); - - // Set the file property explicitly. - properties.setProperty(Options.FILE, file.toString()); - - stores[i] = newJournal(properties); - - } - - return stores[0]; - - } - -// /** -// * Begin to run as part of a highly available {@link Quorum}. -// * -// * @param newQuorum -// * The {@link Quorum}. -// */ -// public void joinQuorum(final Quorum<HAGlue, QuorumService<HAGlue>> quorum) { -// -// if (quorum == null) -// throw new IllegalArgumentException(); -// -// final WriteLock lock = _fieldReadWriteLock.writeLock(); -// -// lock.lock(); -// -// try { -// -// if (this.quorum.get() != null) { -// // Already running with some quorum. -// throw new IllegalStateException(); -// } -// -// // discard the current write set. -// abort(); -// -// // set the quorum object. -// this.quorum.set(quorum); -// -// // save off the current token (typically NO_QUORUM unless standalone). -// quorumToken = quorum.token(); -// -// /* -// * Tell the actor to try and join the quorum. It will join iff our -// * current root block can form a simple majority with the other -// * services in the quorum. -// */ -// final QuorumActor<?,?> actor = quorum.getActor(); -// actor.memberAdd(); -// actor.pipelineAdd(); -// actor.castVote(getRootBlockView().getLastCommitTime()); -// -// } catch (Throwable e) { -// -// throw new RuntimeException(e); -// -// } finally { -// -// lock.unlock(); -// -// } -// -// } - -} \ No newline at end of file Modified: branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/ha/HABranch.txt =================================================================== --- branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/ha/HABranch.txt 2013-12-09 20:53:38 UTC (rev 7629) +++ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/ha/HABranch.txt 2013-12-10 21:36:50 UTC (rev 7630) @@ -388,57 +388,12 @@ TODO: - - RWStore, write cache, write replication, standalone HA in - JOURNAL_HA_BRANCH. - - - The RW store needs to record delete blocks and needs a thread, - periodic task, or commit time task for releasing old commit - points. (Will be done with allocation block bitmap deltas, but - must retain session for resynchronization to be possible.) - - - WORM checksums. Historical WORM stores will not support this so - it needs to be captured by the WORM version number. - - - WORM integration with the write cache service. - - - WriteCacheService lock, sleep and possible gap and deadlock - issues. - - - Interrupted during sleep logs error. - - - WARN : 6938 main - com.bigdata.io.WriteCache.resetWith(WriteCache.java:1368): - Written WriteCache but with no records - - RW is always using 6 buffers. This must be a configuration option so we can stress test the WriteCacheService under heavy write loads and mixed write/read loads with lots of concurrency and only a few buffers. We need to do this to look for deadlocks. - - AbstractJournal: Modify to log the root block to be overwritten - during the commit protocol so we can potentially restore it - from the file. This is easier to do for the WORM and would - require a search of the appropriate allocation block's records - for the RW looking for anything which has the right magic value - and can also be interpreted as a RootBlockView (passes the - checksum, etc). - - - API to accept a pipeline update (watch on the children of a - znode for the logical journal) and to notify if you are no - longer the master (SessionExpiredException when you try some - zookeeper operation). Internally, the code has to handle the - join / leave. - - - API for replication and resynchronization writes. Slaves - should verify checksums as calculated by the master. - Differentiate between replication (ascending writes for the - WORM), resynchronization (delta to the end of the file for the - WORM), and write replacement (random write for both). - - - Journal must be aware of master/slave state and whether it is - caught up and can therefore support reads. - - Handle read errors by reading on a peer. Note that some file systems will retry MANY times, which could hang the caller (timed reads? how?). Consider doing replacement writes over @@ -448,96 +403,3 @@ HA. - Report read errors in support of decision making about failure. - -============================================================ - -During BSBM 2785 data load on laptop. 4/20/2010 - -java.lang.RuntimeException: java.util.concurrent.ExecutionException: java.lang.AssertionError: There are 2 outstanding permits (should be just one). - at com.bigdata.rdf.spo.SPORelation.insert(SPORelation.java:1826) - at com.bigdata.rdf.store.AbstractTripleStore.addStatements(AbstractTripleStore.java:3261) - at com.bigdata.rdf.rio.StatementBuffer.writeSPOs(StatementBuffer.java:989) - at com.bigdata.rdf.rio.StatementBuffer.addStatements(StatementBuffer.java:869) - at com.bigdata.rdf.rio.StatementBuffer.incrementalWrite(StatementBuffer.java:708) - at com.bigdata.rdf.rio.StatementBuffer.add(StatementBuffer.java:784) - at com.bigdata.rdf.rio.StatementBuffer.add(StatementBuffer.java:766) - at com.bigdata.rdf.sail.BigdataSail$BigdataSailConnection.addStatement(BigdataSail.java:1918) - at com.bigdata.rdf.sail.BigdataSail$BigdataSailConnection.addStatement(BigdataSail.java:1879) - at org.openrdf.repository.sail.SailRepositoryConnection.addWithoutCommit(SailRepositoryConnection.java:228) - at org.openrdf.repository.base.RepositoryConnectionBase.add(RepositoryConnectionBase.java:455) - at org.openrdf.repository.util.RDFInserter.handleStatement(RDFInserter.java:196) - at org.openrdf.rio.ntriples.NTriplesParser.parseTriple(NTriplesParser.java:260) - at org.openrdf.rio.ntriples.NTriplesParser.parse(NTriplesParser.java:170) - at org.openrdf.rio.ntriples.NTriplesParser.parse(NTriplesParser.java:112) - at org.openrdf.repository.base.RepositoryConnectionBase.addInputStreamOrReader(RepositoryConnectionBase.java:353) - at org.openrdf.repository.base.RepositoryConnectionBase.add(RepositoryConnectionBase.java:242) - at org.openrdf.repository.base.RepositoryConnectionBase.add(RepositoryConnectionBase.java:239) - at org.openrdf.repository.base.RepositoryConnectionBase.add(RepositoryConnectionBase.java:202) - at benchmark.bigdata.BigdataLoader.loadData(BigdataLoader.java:159) - at benchmark.bigdata.BigdataLoader.main(BigdataLoader.java:109) -Caused by: java.util.concurrent.ExecutionException: java.lang.AssertionError: There are 2 outstanding permits (should be just one). - at java.util.concurrent.FutureTask$Sync.innerGet(FutureTask.java:222) - at java.util.concurrent.FutureTask.get(FutureTask.java:83) - at com.bigdata.rdf.spo.SPORelation.insert(SPORelation.java:1807) - ... 20 more -Caused by: java.lang.AssertionError: There are 2 outstanding permits (should be just one). - at com.bigdata.io.WriteCacheService.writeChk(WriteCacheService.java:834) - at com.bigdata.rwstore.RWStore.alloc(RWStore.java:854) - at com.bigdata.journal.RWStrategy.write(RWStrategy.java:201) - at com.bigdata.journal.AbstractJournal.write(AbstractJournal.java:2498) - at com.bigdata.btree.AbstractBTree.writeNodeOrLeaf(AbstractBTree.java:3664) - at com.bigdata.btree.AbstractBTree.writeNodeRecursive(AbstractBTree.java:3477) - at com.bigdata.btree.DefaultEvictionListener.evicted(DefaultEvictionListener.java:102) - at com.bigdata.btree.DefaultEvictionListener.evicted(DefaultEvictionListener.java:1) - at com.bigdata.cache.HardReferenceQueue.evict(HardReferenceQueue.java:226) - at com.bigdata.cache.HardReferenceQueue.beforeOffer(HardReferenceQueue.java:199) - at com.bigdata.cache.RingBuffer.add(RingBuffer.java:159) - at com.bigdata.cache.HardReferenceQueue.add(HardReferenceQueue.java:176) - at com.bigdata.btree.AbstractBTree.doTouch(AbstractBTree.java:3365) - at com.bigdata.btree.AbstractBTree.touch(AbstractBTree.java:3331) - at com.bigdata.btree.AbstractNode.<init>(AbstractNode.java:297) - at com.bigdata.btree.AbstractNode.<init>(AbstractNode.java:333) - at com.bigdata.btree.Leaf.<init>(Leaf.java:345) - at com.bigdata.btree.AbstractNode.copyOnWrite(AbstractNode.java:492) - at com.bigdata.btree.AbstractNode.copyOnWrite(AbstractNode.java:417) - at com.bigdata.btree.Leaf.insert(Leaf.java:490) - at com.bigdata.btree.Node.insert(Node.java:900) - at com.bigdata.btree.Node.insert(Node.java:900) - at com.bigdata.btree.Node.insert(Node.java:900) - at com.bigdata.btree.AbstractBTree.insert(AbstractBTree.java:2006) - at com.bigdata.btree.AbstractBTree.insert(AbstractBTree.java:1950) - at com.bigdata.rdf.spo.SPOIndexWriteProc.apply(SPOIndexWriteProc.java:247) - at com.bigdata.btree.UnisolatedReadWriteIndex.submit(UnisolatedReadWriteIndex.java:796) - at com.bigdata.rdf.spo.SPOIndexWriter.call(SPOIndexWriter.java:329) - at com.bigdata.rdf.spo.SPOIndexWriter.call(SPOIndexWriter.java:1) - at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:303) - at java.util.concurrent.FutureTask.run(FutureTask.java:138) - at java.util.concurrent.ThreadPoolExecutor$Worker.runTask(ThreadPoolExecutor.java:886) - at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:908) - at java.lang.Thread.run(Thread.java:619) -ERROR: 37844 com.bigdata.rwstore.RWWriteCacheService1 com.bigdata.io.WriteCacheService$WriteTask.call(WriteCacheService.java:307): java.nio.channels.ClosedByInterruptException -java.nio.channels.ClosedByInterruptException - at java.nio.channels.spi.AbstractInterruptibleChannel.end(AbstractInterruptibleChannel.java:184) - at sun.nio.ch.FileChannelImpl.write(FileChannelImpl.java:653) - at com.bigdata.io.FileChannelUtility.writeAll(FileChannelUtility.java:402) - at com.bigdata.io.WriteCache$FileChannelScatteredWriteCache.writeOnChannel(WriteCache.java:1313) - at com.bigdata.io.WriteCache.flushAndReset(WriteCache.java:745) - at com.bigdata.io.WriteCache.flush(WriteCache.java:658) - at com.bigdata.io.WriteCache.flush(WriteCache.java:604) - at com.bigdata.io.WriteCacheService$WriteTask.call(WriteCacheService.java:285) - at com.bigdata.io.WriteCacheService$WriteTask.call(WriteCacheService.java:1) - at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:303) - at java.util.concurrent.FutureTask.run(FutureTask.java:138) - at java.util.concurrent.ThreadPoolExecutor$Worker.runTask(ThreadPoolExecutor.java:886) - at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:908) - at java.lang.Thread.run(Thread.java:619) -ERROR: 37844 com.bigdata.rwstore.RWWriteCacheService1 com.bigdata.io.WriteCacheService$WriteTask.call(WriteCacheService.java:307): java.lang.InterruptedException: sleep interrupted -java.lang.InterruptedException: sleep interrupted - at java.lang.Thread.sleep(Native Method) - at com.bigdata.io.WriteCacheService$WriteTask.call(WriteCacheService.java:271) - at com.bigdata.io.WriteCacheService$WriteTask.call(WriteCacheService.java:1) - at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:303) - at java.util.concurrent.FutureTask.run(FutureTask.java:138) - at java.util.concurrent.ThreadPoolExecutor$Worker.runTask(ThreadPoolExecutor.java:886) - at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:908) - at java.lang.Thread.run(Thread.java:619) Deleted: branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/ha/TestAll.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/ha/TestAll.java 2013-12-09 20:53:38 UTC (rev 7629) +++ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/ha/TestAll.java 2013-12-10 21:36:50 UTC (rev 7630) @@ -1,74 +0,0 @@ -/** - -Copyright (C) SYSTAP, LLC 2006-2007. All rights reserved. - -Contact: - SYSTAP, LLC - 4501 Tower Road - Greensboro, NC 27410 - lic...@bi... - -This program is free software; you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation; version 2 of the License. - -This program is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. - -You should have received a copy of the GNU General Public License -along with this program; if not, write to the Free Software -Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA -*/ -/* - * Created on Oct 14, 2006 - */ - -package com.bigdata.journal.ha; - -import junit.framework.Test; -import junit.framework.TestCase; -import junit.framework.TestSuite; - -/** - * Runs all tests for all journal implementations. - * - * @author <a href="mailto:tho...@us...">Bryan Thompson</a> - * @version $Id$ - */ -public class TestAll extends TestCase { - - /** - * - */ - public TestAll() { - } - - /** - * @param arg0 - */ - public TestAll(String arg0) { - super(arg0); - } - - /** - * Returns a test that will run each of the implementation specific test - * suites in turn. - */ - public static Test suite() - { - - final TestSuite suite = new TestSuite("journal/HA"); - - // HA test suite for the WORM strategy. - suite.addTest(TestHAWORMStrategy.suite()); - - // @todo HA test suite for the RW strategy. -// suite.addTest(TestHARWStrategy.suite()); - - return suite; - - } - -} Deleted: branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/ha/TestHAWORMStrategy.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/ha/TestHAWORMStrategy.java 2013-12-09 20:53:38 UTC (rev 7629) +++ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/ha/TestHAWORMStrategy.java 2013-12-10 21:36:50 UTC (rev 7630) @@ -1,378 +0,0 @@ -/** - -Copyright (C) SYSTAP, LLC 2006-2007. All rights reserved. - -Contact: - SYSTAP, LLC - 4501 Tower Road - Greensboro, NC 27410 - lic...@bi... - -This program is free software; you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation; version 2 of the License. - -This program is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. - -You should have received a copy of the GNU General Public License -along with this program; if not, write to the Free Software -Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA -*/ -/* - * Created on Oct 14, 2006 - */ - -package com.bigdata.journal.ha; - -import java.io.File; -import java.io.IOException; -import java.util.Properties; - -import junit.extensions.proxy.ProxyTestSuite; -import junit.framework.Test; - -import com.bigdata.io.DirectBufferPool; -import com.bigdata.io.writecache.WriteCacheService; -import com.bigdata.journal.AbstractInterruptsTestCase; -import com.bigdata.journal.AbstractMRMWTestCase; -import com.bigdata.journal.AbstractMROWTestCase; -import com.bigdata.journal.AbstractRestartSafeTestCase; -import com.bigdata.journal.BufferMode; -import com.bigdata.journal.Journal; -import com.bigdata.journal.Options; -import com.bigdata.journal.TestJournalBasics; -import com.bigdata.journal.WORMStrategy; -import com.bigdata.rawstore.IRawStore; - -/** - * Test suite for highly available {@link WORMStrategy} journals. - * - * @author <a href="mailto:tho...@us...">Bryan Thompson</a> - * @version $Id$ - */ -public class TestHAWORMStrategy extends AbstractHAJournalTestCase { - - public TestHAWORMStrategy() { - super(); - } - - public TestHAWORMStrategy(String name) { - super(name); - } - - public static Test suite() { - - final TestHAWORMStrategy delegate = new TestHAWORMStrategy(); // !!!! THIS CLASS !!!! - - /* - * Use a proxy test suite and specify the delegate. - */ - - final ProxyTestSuite suite = new ProxyTestSuite(delegate, - "WORM HA Journal Test Suite"); - - /* - * List any non-proxied tests (typically bootstrapping tests). - */ - -// /* -// * HA bootstrap test (non-proxied). -// */ -// suite.addTestSuite(TestHAJournalBootstrap.class); - - /* - * Proxied test suites. - */ - - // tests defined by this class. - suite.addTestSuite(TestHAWORMStrategy.class); - - // test suite for the IRawStore api. - suite.addTestSuite(TestRawStore.class); - - // test suite for handling asynchronous close of the file channel. - suite.addTestSuite(TestInterrupts.class); - - // test suite for MROW correctness. - suite.addTestSuite(TestMROW.class); - - // test suite for MRMW correctness. - suite.addTestSuite(TestMRMW.class); - - /* - * Pickup the basic journal test suite. This is a proxied test suite, so - * all the tests will run with the configuration specified in this test - * class and its optional .properties file. - */ - suite.addTest(TestJournalBasics.suite()); - - /* - * Pickup the HA journal test suite. - */ - suite.addTest(TestJournalHA.suite()); - - return suite; - - } - - public Properties getProperties() { - - final Properties properties = super.getProperties(); - - properties.setProperty(Journal.Options.COLLECT_PLATFORM_STATISTICS, - "false"); - - properties.setProperty(Journal.Options.COLLECT_QUEUE_STATISTICS, - "false"); - - properties.setProperty(Journal.Options.HTTPD_PORT, "-1"/* none */); - - properties.setProperty(Options.BUFFER_MODE, BufferMode.DiskWORM.toString()); - - properties.setProperty(Options.CREATE_TEMP_FILE, "true"); - - properties.setProperty(Options.DELETE_ON_EXIT, "true"); - - properties.setProperty(Options.WRITE_CACHE_ENABLED, "" - + writeCacheEnabled); - - return properties; - - } - - /** - * Verify normal operation and basic assumptions when creating a new journal - * using {@link BufferMode#DiskWORM}. - * - * @throws IOException - */ - public void test_create_disk01() throws IOException { - - final Properties properties = getProperties(); - - final Journal journal = new Journal(properties); - - try { - - final WORMStrategy bufferStrategy = (WORMStrategy) journal - .getBufferStrategy(); - - assertTrue("isStable", bufferStrategy.isStable()); - assertFalse("isFullyBuffered", bufferStrategy.isFullyBuffered()); - // assertEquals(Options.FILE, properties.getProperty(Options.FILE), - // bufferStrategy.file.toString()); - assertEquals(Options.INITIAL_EXTENT, Long - .parseLong(Options.DEFAULT_INITIAL_EXTENT), bufferStrategy - .getInitialExtent()); - assertEquals(Options.MAXIMUM_EXTENT, - 0L/* soft limit for disk mode */, bufferStrategy - .getMaximumExtent()); - assertNotNull("raf", bufferStrategy.getRandomAccessFile()); - assertEquals(Options.BUFFER_MODE, BufferMode.DiskWORM, bufferStrategy - .getBufferMode()); - - } finally { - - journal.destroy(); - - } - - } - - /** - * Unit test verifies that {@link Options#CREATE} may be used to initialize - * a journal on a newly created empty file. - * - * @throws IOException - */ - public void test_create_emptyFile() throws IOException { - - final File file = File.createTempFile(getName(), Options.JNL); - - final Properties properties = new Properties(); - - properties.setProperty(Options.BUFFER_MODE, BufferMode.DiskWORM.toString()); - - properties.setProperty(Options.FILE, file.toString()); - - properties.setProperty(Options.WRITE_CACHE_ENABLED, "" - + writeCacheEnabled); - - final Journal journal = new Journal(properties); - - try { - - assertEquals(file, journal.getFile()); - - } finally { - - journal.destroy(); - - } - - } - - /** - * Test suite integration for {@link AbstractRestartSafeTestCase}. - * - * @author <a href="mailto:tho...@us...">Bryan Thompson</a> - * @version $Id$ - */ - public static class TestRawStore extends AbstractRestartSafeTestCase { - - public TestRawStore() { - super(); - } - - public TestRawStore(String name) { - super(name); - } - - protected BufferMode getBufferMode() { - - return BufferMode.DiskWORM; - - } - - } - - /** - * Test suite integration for {@link AbstractInterruptsTestCase}. - * - * @author <a href="mailto:tho...@us...">Bryan Thompson</a> - * @version $Id$ - */ - public static class TestInterrupts extends AbstractInterruptsTestCase { - - public TestInterrupts() { - super(); - } - - public TestInterrupts(String name) { - super(name); - } - - protected IRawStore getStore() { - - final Properties properties = getProperties(); - - properties.setProperty(Options.DELETE_ON_EXIT, "true"); - - properties.setProperty(Options.CREATE_TEMP_FILE, "true"); - - properties.setProperty(Options.BUFFER_MODE, BufferMode.DiskWORM - .toString()); - - properties.setProperty(Options.WRITE_CACHE_ENABLED, "" - + writeCacheEnabled); - - return new Journal(properties);//.getBufferStrategy(); - - } - - } - - /** - * Test suite integration for {@link AbstractMROWTestCase}. - * - * @author <a href="mailto:tho...@us...">Bryan Thompson</a> - * @version $Id$ - */ - public static class TestMROW extends AbstractMROWTestCase { - - public TestMROW() { - super(); - } - - public TestMROW(String name) { - super(name); - } - - protected IRawStore getStore() { - - final Properties properties = getProperties(); - - properties.setProperty(Options.CREATE_TEMP_FILE, "true"); - - properties.setProperty(Options.DELETE_ON_EXIT, "true"); - - properties.setProperty(Options.BUFFER_MODE, BufferMode.DiskWORM - .toString()); - - properties.setProperty(Options.WRITE_CACHE_ENABLED, "" - + writeCacheEnabled); - - return new Journal(properties);//.getBufferStrategy(); - - } - - } - - /** - * Test suite integration for {@link AbstractMRMWTestCase}. - * - * @author <a href="mailto:tho...@us...">Bryan Thompson</a> - * @version $Id$ - */ - public static class TestMRMW extends AbstractMRMWTestCase { - - public TestMRMW() { - super(); - } - - public TestMRMW(String name) { - super(name); - } - - protected IRawStore getStore() { - - final Properties properties = getProperties(); - - properties.setProperty(Options.CREATE_TEMP_FILE, "true"); - - properties.setProperty(Options.DELETE_ON_EXIT, "true"); - - properties.setProperty(Options.BUFFER_MODE, BufferMode.DiskWORM - .toString()); - - properties.setProperty(Options.WRITE_CACHE_ENABLED, "" - + writeCacheEnabled); - - /* - * The following two properties are dialed way down in order to - * raise the probability that we will observe the following error - * during this test. - * - * http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=6371642 - * - * FIXME We should make the MRMW test harder and focus on - * interleaving concurrent extensions of the backing store for both - * WORM and R/W stores. - */ - - // Note: Use a relatively small initial extent. - properties.setProperty(Options.INITIAL_EXTENT, "" - + DirectBufferPool.INSTANCE.getBufferCapacity() * 1); - - // Note: Use a relatively small extension each time. - properties.setProperty(Options.MINIMUM_EXTENSION, - "" + (long) (DirectBufferPool.INSTANCE - .getBufferCapacity() * 1.1)); - - return new Journal(properties);//.getBufferStrategy(); - - } - - } - - /** - * Note: HA requires the use of the write cache. It is the - * {@link WriteCacheService} which provides the write replication mechanism - * for HA. - */ - private static final boolean writeCacheEnabled = true; - -} Deleted: branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/ha/TestHAWritePipeline.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/ha/TestHAWritePipeline.java 2013-12-09 20:53:38 UTC (rev 7629) +++ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/ha/TestHAWritePipeline.java 2013-12-10 21:36:50 UTC (rev 7630) @@ -1,370 +0,0 @@ -/** - -Copyright (C) SYSTAP, LLC 2006-2010. All rights reserved. - -Contact: - SYSTAP, LLC - 4501 Tower Road - Greensboro, NC 27410 - lic...@bi... - -This program is free software; you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation; version 2 of the License. - -This program is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. - -You should have received a cop... [truncated message content] |
From: <tho...@us...> - 2013-12-11 16:17:55
|
Revision: 7634 http://bigdata.svn.sourceforge.net/bigdata/?rev=7634&view=rev Author: thompsonbry Date: 2013-12-11 16:17:47 +0000 (Wed, 11 Dec 2013) Log Message: ----------- Modified HAReceiveService to always drain down the payload for the current message if there is a problem with re-replicating the payload to the downstream service. Added code to expose the HAGlue implementation object - this is the object that gets exported. This makes it possible to reach into the HAGlueTestImpl object in some unit tests. See #724 Modified Paths: -------------- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HAReceiveService.java branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/journal/jini/ha/AbstractServer.java branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/journal/jini/ha/HAJournal.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/HAJournalTest.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHA3JustKills.java Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HAReceiveService.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HAReceiveService.java 2013-12-11 15:45:11 UTC (rev 7633) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HAReceiveService.java 2013-12-11 16:17:47 UTC (rev 7634) @@ -983,6 +983,19 @@ private void doReceiveAndReplicate(final Client client) throws Exception { + /** + * The first cause if downstream replication fails. We make a note + * of this first cause, continue to drain the payload, and then + * rethrow the first cause once the payload has been fully drained. + * This is necessary to ensure that the socket channel does not have + * partial data remaining from an undrained payload. + * + * @see <a + * href="https://sourceforge.net/apps/trac/bigdata/ticket/724" + * > HA wire pulling and sure kill testing </a> + */ + Throwable downstreamFirstCause = null; + /* * We should now have parameters ready in the WriteMessage and can * begin transferring data from the stream to the writeCache. @@ -1085,65 +1098,22 @@ callback.incReceive(message, reads, rdlen, rem); } - /* - * Now forward the most recent transfer bytes downstream - * - * @todo Since the downstream writes are against a blocking - * mode channel, the receiver on this node runs in sync with - * the receiver on the downstream node. In fact, those - * processes could be decoupled with a bit more effort and - * are only required to synchronize by the end of each - * received payload. - * - * Note: [addrNext] is final. If the downstream address is - * changed, then the ReadTask is interrupted using its - * Future and the WriteCacheService will handle the error by - * retransmitting the current cache block. - * - * The rdlen is checked for non zero to avoid an - * IllegalArgumentException. - * - * Note: loop since addrNext might change asynchronously. - */ - while(true) { - if (rdlen != 0 && addrNextRef.get() != null) { - if (log.isTraceEnabled()) - log.trace("Incremental send of " + rdlen + " bytes"); - final ByteBuffer out = localBuffer.asReadOnlyBuffer(); - out.position(localBuffer.position() - rdlen); - out.limit(localBuffer.position()); - synchronized (sendService) { - /* - * Note: Code block is synchronized on [downstream] - * to make the decision to start the HASendService - * that relays to [addrNext] atomic. The - * HASendService uses [synchronized] for its public - * methods so we can coordinate this lock with its - * synchronization API. - */ - if (!sendService.isRunning()) { - /* - * Prepare send service for incremental - * transfers to the specified address. - */ - // Check for termination. - client.checkFirstCause(); - // Note: use then current addrNext! - sendService.start(addrNextRef.get()); - continue; - } + if (downstreamFirstCause == null) { + try { + forwardReceivedBytes(client, rdlen); + } catch (ExecutionException ex) { + log.error( + "Downstream replication failure" + + ": will drain payload and then rethrow exception: rootCause=" + + ex, ex); + downstreamFirstCause = ex; } - // Check for termination. - client.checkFirstCause(); - // Send and await Future. - sendService.send(out).get(); - } - break; } - } - } // while( rem > 0 ) + } // while(itr.hasNext()) + } // while( rem > 0 && !EOS ) + if (localBuffer.position() != message.getSize()) throw new IOException("Receive length error: localBuffer.pos=" + localBuffer.position() + ", message.size=" @@ -1164,12 +1134,109 @@ + ", actual=" + (int) chk.getValue()); } + if (downstreamFirstCause != null) { + + /** + * Replication to the downstream service failed. The payload has + * been fully drained. This ensures that we do not leave part of + * the payload in the upstream socket channel. We now wrap and + * rethrow the root cause of the downstream failure. The leader + * will handle this by forcing the remove of the downstream + * service and then re-replicating the payload. + * + * @see <a + * href="https://sourceforge.net/apps/trac/bigdata/ticket/724" + * > HA wire pulling and sure kill testing </a> + */ + + throw new RuntimeException( + "Downstream replication failure: msg=" + message + + ", ex=" + downstreamFirstCause, + downstreamFirstCause); + + } + if (callback != null) { + + /* + * The message was received and (if there is a downstream + * service) successfully replicated to the downstream service. + * We now invoke the callback to given this service an + * opportunity to handle the message and the fully received + * payload. + */ + callback.callback(message, localBuffer); + } } // call() + /** + * Now forward the most recent transfer bytes downstream. + * <p> + * + * Note: [addrNext] is final. If the downstream address is changed, then + * the {@link ReadTask} is interrupted using its {@link Future} and the + * WriteCacheService on the leader will handle the error by + * retransmitting the current cache block. + * + * The rdlen is checked for non zero to avoid an + * IllegalArgumentException. + * + * Note: loop since addrNext might change asynchronously. + * + * @throws ExecutionException + * @throws InterruptedException + * + * @todo Since the downstream writes are against a blocking mode + * channel, the receiver on this node runs in sync with the + * receiver on the downstream node. In fact, those processes could + * be decoupled with a bit more effort and are only required to + * synchronize by the end of each received payload. + * + * @see <a href="https://sourceforge.net/apps/trac/bigdata/ticket/724" > + * HA wire pulling and sure kill testing </a> + */ + private void forwardReceivedBytes(final Client client, final int rdlen) + throws InterruptedException, ExecutionException { + while (true) { + if (rdlen != 0 && addrNextRef.get() != null) { + if (log.isTraceEnabled()) + log.trace("Incremental send of " + rdlen + " bytes"); + final ByteBuffer out = localBuffer.asReadOnlyBuffer(); + out.position(localBuffer.position() - rdlen); + out.limit(localBuffer.position()); + synchronized (sendService) { + /* + * Note: Code block is synchronized on [downstream] to + * make the decision to start the HASendService that + * relays to [addrNext] atomic. The HASendService uses + * [synchronized] for its public methods so we can + * coordinate this lock with its synchronization API. + */ + if (!sendService.isRunning()) { + /* + * Prepare send service for incremental transfers to + * the specified address. + */ + // Check for termination. + client.checkFirstCause(); + // Note: use then current addrNext! + sendService.start(addrNextRef.get()); + continue; + } + } + // Check for termination. + client.checkFirstCause(); + // Send and await Future. + sendService.send(out).get(); + } + break; // break out of the inner while loop. + } // while(true) + + } + // private void ack(final Client client) throws IOException { // // if (log.isTraceEnabled()) Modified: branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/journal/jini/ha/AbstractServer.java =================================================================== --- branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/journal/jini/ha/AbstractServer.java 2013-12-11 15:45:11 UTC (rev 7633) +++ branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/journal/jini/ha/AbstractServer.java 2013-12-11 16:17:47 UTC (rev 7634) @@ -311,12 +311,12 @@ /** * The service implementation object. */ - protected Remote impl; + private Remote impl; /** * The exported proxy for the service implementation object. */ - protected Remote proxy; + private Remote proxy; /** * The name of the host on which the server is running. @@ -349,6 +349,8 @@ /** * The exported proxy for the service implementation object. + * + * @see #getRemoteImpl() */ public Remote getProxy() { @@ -357,6 +359,17 @@ } /** + * The service implementation object. + * + * @see #getProxy() + */ + public Remote getRemoteImpl() { + + return impl; + + } + + /** * Return the assigned {@link ServiceID}. If this is a new service and the * {@link ServiceUUID} was not specified in the {@link Configuration} then * the {@link ServiceID} will be <code>null</code> until it has been Modified: branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/journal/jini/ha/HAJournal.java =================================================================== --- branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/journal/jini/ha/HAJournal.java 2013-12-11 15:45:11 UTC (rev 7633) +++ branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/journal/jini/ha/HAJournal.java 2013-12-11 16:17:47 UTC (rev 7634) @@ -1949,12 +1949,13 @@ * @return an object that implements whatever administration interfaces * are appropriate for the particular service. */ + @Override public Object getAdmin() throws RemoteException { if (log.isInfoEnabled()) log.info("serviceID=" + server.getServiceID()); - return server.proxy; + return server.getProxy(); } Modified: branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/HAJournalTest.java =================================================================== --- branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/HAJournalTest.java 2013-12-11 15:45:11 UTC (rev 7633) +++ branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/HAJournalTest.java 2013-12-11 16:17:47 UTC (rev 7634) @@ -43,6 +43,7 @@ import java.util.concurrent.atomic.AtomicBoolean; import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicLong; +import java.util.concurrent.atomic.AtomicReference; import net.jini.config.Configuration; import net.jini.config.ConfigurationException; @@ -89,8 +90,8 @@ import com.bigdata.journal.ITx; import com.bigdata.journal.StoreState; import com.bigdata.journal.jini.ha.HAJournalServer.HAQuorumService; +import com.bigdata.journal.jini.ha.HAJournalServer.HAQuorumService.IHAProgressListener; import com.bigdata.journal.jini.ha.HAJournalServer.RunStateEnum; -import com.bigdata.journal.jini.ha.HAJournalServer.HAQuorumService.IHAProgressListener; import com.bigdata.quorum.AsynchronousQuorumCloseException; import com.bigdata.quorum.Quorum; import com.bigdata.quorum.zk.ZKQuorumImpl; @@ -125,6 +126,16 @@ return new HAGlueTestImpl(serviceId); } + + /** + * The service implementation object that gets exported (not the proxy, but + * the thing that gets exported as the {@link HAGlueTest} proxy). + */ + public HAGlueTestImpl getRemoteImpl() { + + return (HAGlueTestImpl) getHAJournalServer().getRemoteImpl(); + + } /** * Utility accessible for HAGlueTest methods and public static for @@ -328,7 +339,21 @@ * Supports consistency checking between HA services */ public StoreState getStoreState() throws IOException; - + + /** + * Gets and clears a root cause that was set on the remote service. This + * is used to inspect the root cause when an RMI method is interrupted + * in the local JVM. Since the RMI was interrupted, we can not observe + * the outcome or root cause of the associated failure on the remote + * service. However, test glue can explicitly set that root cause such + * that it can then be reported using this method. + */ + public Throwable getAndClearLastRootCause() throws IOException; + + /** + * Variant that does not clear out the last root cause. + */ + public Throwable getLastRootCause() throws IOException; } /** @@ -437,7 +462,7 @@ * * @see HAJournal.HAGlueService */ - private class HAGlueTestImpl extends HAJournal.HAGlueService + class HAGlueTestImpl extends HAJournal.HAGlueService implements HAGlue, HAGlueTest, RemoteDestroyAdmin { /** @@ -479,7 +504,7 @@ false); private final AtomicLong nextTimestamp = new AtomicLong(-1L); - + private HAGlueTestImpl(final UUID serviceId) { super(serviceId); @@ -1350,7 +1375,45 @@ .set(listener); } + + @Override + public Throwable getAndClearLastRootCause() throws IOException { + + final Throwable t = lastRootCause.getAndSet(null/* newValue */); + + if (t != null) + log.warn("lastRootCause: " + t, t); + + return t; + + } + @Override + public Throwable getLastRootCause() throws IOException { + + final Throwable t = lastRootCause.get(); + + if (t != null) + log.warn("lastRootCause: " + t, t); + + return t; + + } + public void setLastRootCause(final Throwable t) { + + if (log.isInfoEnabled()) + log.info("Setting lastRootCause: " + t); + + lastRootCause.set(t); + + } + + /** + * @see HAGlueTest#getAndClearLastRootCause() + */ + private AtomicReference<Throwable> lastRootCause = new AtomicReference<Throwable>(); + + } // class HAGlueTestImpl /** Modified: branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHA3JustKills.java =================================================================== --- branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHA3JustKills.java 2013-12-11 15:45:11 UTC (rev 7633) +++ branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHA3JustKills.java 2013-12-11 16:17:47 UTC (rev 7634) @@ -47,149 +47,148 @@ */ public class TestHA3JustKills extends AbstractHA3JournalServerTestCase { - - /** - * {@inheritDoc} - * <p> - * Note: This overrides some {@link Configuration} values for the - * {@link HAJournalServer} in order to establish conditions suitable for - * testing the {@link ISnapshotPolicy} and {@link IRestorePolicy}. - */ - @Override - protected String[] getOverrides() { - - return new String[]{ + /** + * {@inheritDoc} + * <p> + * Note: This overrides some {@link Configuration} values for the + * {@link HAJournalServer} in order to establish conditions suitable for + * testing the {@link ISnapshotPolicy} and {@link IRestorePolicy}. + */ + @Override + protected String[] getOverrides() { + + return new String[]{ // "com.bigdata.journal.HAJournal.properties=" +TestHA3JournalServer.getTestHAJournalProperties(com.bigdata.journal.HAJournal.properties), - "com.bigdata.journal.jini.ha.HAJournalServer.restorePolicy=new com.bigdata.journal.jini.ha.DefaultRestorePolicy(0L,1,0)", - "com.bigdata.journal.jini.ha.HAJournalServer.snapshotPolicy=new com.bigdata.journal.jini.ha.NoSnapshotPolicy()", + "com.bigdata.journal.jini.ha.HAJournalServer.restorePolicy=new com.bigdata.journal.jini.ha.DefaultRestorePolicy(0L,1,0)", + "com.bigdata.journal.jini.ha.HAJournalServer.snapshotPolicy=new com.bigdata.journal.jini.ha.NoSnapshotPolicy()", // "com.bigdata.journal.jini.ha.HAJournalServer.HAJournalClass=\""+HAJournalTest.class.getName()+"\"", - "com.bigdata.journal.jini.ha.HAJournalServer.onlineDisasterRecovery=true", - }; - - } - - public TestHA3JustKills() { - } + "com.bigdata.journal.jini.ha.HAJournalServer.onlineDisasterRecovery=true", + }; + + } + + public TestHA3JustKills() { + } - public TestHA3JustKills(String name) { - super(name); - } + public TestHA3JustKills(String name) { + super(name); + } - /** - * Start A+B+C in strict sequence. Wait until the quorum fully meets. Start - * a long running LOAD. While the LOAD is running, sure kill C (the last - * follower). Verify that the LOAD completes successfully with the remaining - * services (A+B). - */ - public void testABC_LiveLoadRemainsMet_kill_C() throws Exception { + /** + * Start A+B+C in strict sequence. Wait until the quorum fully meets. Start + * a long running LOAD. While the LOAD is running, sure kill C (the last + * follower). Verify that the LOAD completes successfully with the remaining + * services (A+B). + */ + public void testABC_LiveLoadRemainsMet_kill_C() throws Exception { - // enforce join order - final ABC startup = new ABC(true /*sequential*/); - - final long token = awaitFullyMetQuorum(); - - // start concurrent task loads that continue until fully met - final FutureTask<Void> ft = new FutureTask<Void>(new LargeLoadTask( - token)); + // enforce join order + final ABC startup = new ABC(true /*sequential*/); + + final long token = awaitFullyMetQuorum(); + + // start concurrent task loads that continue until fully met + final FutureTask<Void> ft = new FutureTask<Void>(new LargeLoadTask( + token)); - executorService.submit(ft); + executorService.submit(ft); - // allow load head start - Thread.sleep(300/* ms */); + // allow load head start + Thread.sleep(300/* ms */); - // Verify load is still running. - assertFalse(ft.isDone()); - - // Dump Zookeeper - log.warn("ZOOKEEPER\n" + dumpZoo()); - - kill(startup.serverC); - - // FIXME: in the face of no implemented error propagation we can explicitly - // tell the leader to remove the killed service! - startup.serverA.submit(new ForceRemoveService(getServiceCId()), true).get(); + // Verify load is still running. + assertFalse(ft.isDone()); + + // Dump Zookeeper + log.warn("ZOOKEEPER\n" + dumpZoo()); + + kill(startup.serverC); + + // FIXME: in the face of no implemented error propagation we can explicitly + // tell the leader to remove the killed service! + startup.serverA.submit(new ForceRemoveService(getServiceCId()), true).get(); - awaitPipeline(20, TimeUnit.SECONDS, new HAGlue[] {startup.serverA, startup.serverB}); + awaitPipeline(20, TimeUnit.SECONDS, new HAGlue[] {startup.serverA, startup.serverB}); - // token must remain unchanged to indicate same quorum - assertEquals(token, awaitMetQuorum()); + // token must remain unchanged to indicate same quorum + assertEquals(token, awaitMetQuorum()); - awaitMembers(new HAGlue[] {startup.serverA, startup.serverB}); - awaitJoined(new HAGlue[] {startup.serverA, startup.serverB}); + awaitMembers(new HAGlue[] {startup.serverA, startup.serverB}); + awaitJoined(new HAGlue[] {startup.serverA, startup.serverB}); - // token must remain unchanged to indicate same quorum - assertEquals(token, awaitMetQuorum()); - - // Await LOAD, but with a timeout. - ft.get(longLoadTimeoutMillis, TimeUnit.MILLISECONDS); + // token must remain unchanged to indicate same quorum + assertEquals(token, awaitMetQuorum()); + + // Await LOAD, but with a timeout. + ft.get(longLoadTimeoutMillis, TimeUnit.MILLISECONDS); - // token must remain unchanged to indicate same quorum - assertEquals(token, awaitMetQuorum()); + // token must remain unchanged to indicate same quorum + assertEquals(token, awaitMetQuorum()); - } - - public void testStressABC_LiveLoadRemainsMet_kill_C() throws Exception { - for (int i = 0; i < 5; i++) { - try { - testABC_LiveLoadRemainsMet_kill_C(); - } catch (Throwable t) { - fail("Run " + i, t); - } finally { - Thread.sleep(1000); - destroyAll(); - } - } - } + } + + public void _testStressABC_LiveLoadRemainsMet_kill_C() throws Exception { + for (int i = 0; i < 5; i++) { + try { + testABC_LiveLoadRemainsMet_kill_C(); + } catch (Throwable t) { + fail("Run " + i, t); + } finally { + Thread.sleep(1000); + destroyAll(); + } + } + } - /** - * Start A+B+C in strict sequence. Wait until the quorum fully meets. Start - * a long running LOAD. While the LOAD is running, sure kill B (the first - * follower). Verify that the LOAD completes successfully with the remaining - * services (A+C), after the leader re-orders the pipeline. - */ - public void testABC_LiveLoadRemainsMet_kill_B() throws Exception { + /** + * Start A+B+C in strict sequence. Wait until the quorum fully meets. Start + * a long running LOAD. While the LOAD is running, sure kill B (the first + * follower). Verify that the LOAD completes successfully with the remaining + * services (A+C), after the leader re-orders the pipeline. + */ + public void testABC_LiveLoadRemainsMet_kill_B() throws Exception { - // enforce join order - final ABC startup = new ABC(true /*sequential*/); - - final long token = awaitFullyMetQuorum(); - - // start concurrent task loads that continue until fully met - final FutureTask<Void> ft = new FutureTask<Void>(new LargeLoadTask( - token)); + // enforce join order + final ABC startup = new ABC(true /*sequential*/); + + final long token = awaitFullyMetQuorum(); + + // start concurrent task loads that continue until fully met + final FutureTask<Void> ft = new FutureTask<Void>(new LargeLoadTask( + token)); - executorService.submit(ft); + executorService.submit(ft); - // allow load head start - Thread.sleep(1000/* ms */); + // allow load head start + Thread.sleep(1000/* ms */); - // Verify load is still running. - assertFalse(ft.isDone()); - - // Dump Zookeeper - log.warn("ZOOKEEPER\n" + dumpZoo()); - - kill(startup.serverB); - - // FIXME: temporary call to explicitly remove the service prior to correct protocol - startup.serverA.submit(new ForceRemoveService(getServiceBId()), true).get(); + // Verify load is still running. + assertFalse(ft.isDone()); + + // Dump Zookeeper + log.warn("ZOOKEEPER\n" + dumpZoo()); + + kill(startup.serverB); + + // FIXME: temporary call to explicitly remove the service prior to correct protocol + startup.serverA.submit(new ForceRemoveService(getServiceBId()), true).get(); - awaitPipeline(10, TimeUnit.SECONDS, new HAGlue[] {startup.serverA, startup.serverC}); - - // also check members and joined - awaitMembers(new HAGlue[] {startup.serverA, startup.serverC}); - awaitJoined(new HAGlue[] {startup.serverA, startup.serverC}); + awaitPipeline(10, TimeUnit.SECONDS, new HAGlue[] {startup.serverA, startup.serverC}); + + // also check members and joined + awaitMembers(new HAGlue[] {startup.serverA, startup.serverC}); + awaitJoined(new HAGlue[] {startup.serverA, startup.serverC}); - // token must remain unchanged to indicate same quorum - assertEquals(token, awaitMetQuorum()); - - // Await LOAD, but with a timeout. - ft.get(longLoadTimeoutMillis, TimeUnit.MILLISECONDS); + // token must remain unchanged to indicate same quorum + assertEquals(token, awaitMetQuorum()); + + // Await LOAD, but with a timeout. + ft.get(longLoadTimeoutMillis, TimeUnit.MILLISECONDS); - // token must remain unchanged to indicate same quorum - assertEquals(token, awaitMetQuorum()); + // token must remain unchanged to indicate same quorum + assertEquals(token, awaitMetQuorum()); - } + } /** * Base class for sure kill of a process when write replication reaches a @@ -243,8 +242,13 @@ log.error("msg=" + msg + ", nreads=" + nreads + ", rdlen=" + rdlen + ", rem=" + rem); - // Note: This is the *opening* root block counter. - if (msg.getCommitCounter() == 1L && nreads > 1) { + /* + * Note: This is the *opening* root block counter. The process will + * be killed as soon as it has received the first chunk of data for + * the payload of the first replicated write cache block. + */ + + if (msg.getCommitCounter() == 1L) { sureKill(); This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |
From: <tho...@us...> - 2013-12-12 23:38:58
|
Revision: 7636 http://bigdata.svn.sourceforge.net/bigdata/?rev=7636&view=rev Author: thompsonbry Date: 2013-12-12 23:38:47 +0000 (Thu, 12 Dec 2013) Log Message: ----------- Sync to Martyn and CI on #724 (write replication pipeline resynchronization). We have incorporated logic to drain to the marker in the replication protocol. The marker concept has been refactored. There is now an IHASendState that captures original and potentially routing information for the payload. This has been raised into the HAPipelineGlue interface. We still need to bring in the typed exception handling for forceRemoveService() invocations and examine QuorumPipelineImpl for possible lock contention issues around this resync protocol. Removed dead test suite from build.xml Modified Paths: -------------- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/HAPipelineGlue.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipeline.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumServiceBase.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/HAWriteMessage.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/HAWriteMessageBase.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HAReceiveService.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HASendService.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/journal/AbstractJournal.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/ha/pipeline/TestHASendAndReceive.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/ha/pipeline/TestHASendAndReceive3Nodes.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/ha/pipeline/TestSocketsDirect.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/io/writecache/TestWORMWriteCacheService.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/quorum/MockQuorumFixture.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/HAJournalTest.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHA3JustKills.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/quorum/zk/MockQuorumMember.java branches/MGC_1_3_0/build.xml Added Paths: ----------- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/HAMessageWrapper.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/HASendState.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/IHAMessageWrapper.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/IHASendState.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/ha/pipeline/AbstractHASendAndReceiveTestCase.java Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/HAPipelineGlue.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/HAPipelineGlue.java 2013-12-11 16:31:29 UTC (rev 7635) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/HAPipelineGlue.java 2013-12-12 23:38:47 UTC (rev 7636) @@ -37,6 +37,7 @@ import com.bigdata.ha.msg.IHALogRootBlocksRequest; import com.bigdata.ha.msg.IHALogRootBlocksResponse; import com.bigdata.ha.msg.IHARebuildRequest; +import com.bigdata.ha.msg.IHASendState; import com.bigdata.ha.msg.IHASendStoreResponse; import com.bigdata.ha.msg.IHASyncRequest; import com.bigdata.ha.msg.IHAWriteMessage; @@ -128,14 +129,17 @@ * A request for an HALog (optional). This is only non-null when * historical {@link WriteCache} blocks are being replayed down * the write pipeline in order to synchronize a service. + * @param snd + * Metadata about the state of the sender and potentially the + * routing of the payload along the write replication pipeline. * @param msg * The metadata. * * @return The {@link Future} which will become available once the buffer * transfer is complete. */ - Future<Void> receiveAndReplicate(IHASyncRequest req, IHAWriteMessage msg) - throws IOException; + Future<Void> receiveAndReplicate(IHASyncRequest req, IHASendState snd, + IHAWriteMessage msg) throws IOException; /** * Request metadata about the current write set from the quorum leader. Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipeline.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipeline.java 2013-12-11 16:31:29 UTC (rev 7635) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipeline.java 2013-12-12 23:38:47 UTC (rev 7636) @@ -33,6 +33,7 @@ import java.util.concurrent.Future; import com.bigdata.ha.halog.HALogWriter; +import com.bigdata.ha.msg.IHASendState; import com.bigdata.ha.msg.IHASyncRequest; import com.bigdata.ha.msg.IHAWriteMessage; import com.bigdata.io.writecache.WriteCache; @@ -85,11 +86,14 @@ * A synchronization request (optional). This is only non-null * when historical {@link WriteCache} blocks are being replayed * down the write pipeline in order to synchronize a service. + * @param snd + * Metadata about the state of the sender and potentially the + * routing of the payload along the write replication pipeline. * @param msg * The RMI metadata about the payload. */ - Future<Void> receiveAndReplicate(IHASyncRequest req, IHAWriteMessage msg) - throws IOException; + Future<Void> receiveAndReplicate(IHASyncRequest req, IHASendState snd, + IHAWriteMessage msg) throws IOException; /* * Note: Method removed since it does not appear necessary to let this Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java 2013-12-11 16:31:29 UTC (rev 7635) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java 2013-12-12 23:38:47 UTC (rev 7636) @@ -41,15 +41,17 @@ import java.util.concurrent.RunnableFuture; import java.util.concurrent.TimeUnit; import java.util.concurrent.TimeoutException; +import java.util.concurrent.atomic.AtomicLong; import java.util.concurrent.atomic.AtomicReference; import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReentrantLock; import org.apache.log4j.Logger; -import com.bigdata.ha.msg.HAWriteMessageBase; -import com.bigdata.ha.msg.IHALogRequest; +import com.bigdata.ha.msg.HAMessageWrapper; +import com.bigdata.ha.msg.HASendState; import com.bigdata.ha.msg.IHAMessage; +import com.bigdata.ha.msg.IHASendState; import com.bigdata.ha.msg.IHASyncRequest; import com.bigdata.ha.msg.IHAWriteMessage; import com.bigdata.ha.pipeline.HAReceiveService; @@ -190,7 +192,7 @@ * href="https://sourceforge.net/apps/trac/bigdata/ticket/724">HA wire * pulling and sudden kill testing</a>. */ - private final int RETRY_SLEEP = 100; //200; // 50; // milliseconds. + private final int RETRY_SLEEP = 30; //200; // 50; // milliseconds. /** * Once this timeout is elapsed, retrySend() will fail. @@ -207,12 +209,12 @@ /** * The {@link QuorumMember}. */ - protected final QuorumMember<S> member; + private final QuorumMember<S> member; /** * The service {@link UUID} for the {@link QuorumMember}. */ - protected final UUID serviceId; + private final UUID serviceId; /** * Lock managing the various mutable aspects of the pipeline state. @@ -244,6 +246,11 @@ private final InnerEventHandler innerEventHandler = new InnerEventHandler(); /** + * One up message identifier. + */ + private final AtomicLong messageId = new AtomicLong(0L); + + /** * Core implementation of the handler for the various events. Always run * while holding the {@link #lock}. * @@ -851,15 +858,19 @@ public void callback(final HAMessageWrapper msg, final ByteBuffer data) throws Exception { // delegate handling of write cache blocks. - handleReplicatedWrite(msg.req, msg.msg, data); + handleReplicatedWrite(msg.getHASyncRequest(), + (IHAWriteMessage) msg + .getHAWriteMessage(), data); } @Override public void incReceive(final HAMessageWrapper msg, final int nreads, final int rdlen, final int rem) throws Exception { // delegate handling of incremental receive notify. - QuorumPipelineImpl.this.incReceive(msg.req, - msg.msg, nreads, rdlen, rem); + QuorumPipelineImpl.this.incReceive(// + msg.getHASyncRequest(), + (IHAWriteMessage) msg.getHAWriteMessage(), // + nreads, rdlen, rem); } }); // Start the receive service - will not return until service is @@ -1170,36 +1181,17 @@ /* * End of QuorumStateChangeListener. */ - - /** - * Glue class wraps the {@link IHAWriteMessage} and the - * {@link IHALogRequest} message and exposes the requires {@link IHAMessage} - * interface to the {@link HAReceiveService}. This class is never persisted. - * It just let's us handshake with the {@link HAReceiveService} and get back - * out the original {@link IHAWriteMessage} as well as the optional - * {@link IHALogRequest} message. - * - * @author <a href="mailto:tho...@us...">Bryan - * Thompson</a> - */ - private static class HAMessageWrapper extends HAWriteMessageBase { - private static final long serialVersionUID = 1L; + private IHASendState newSendState() { - final IHASyncRequest req; - final IHAWriteMessage msg; - - public HAMessageWrapper(final IHASyncRequest req, - final IHAWriteMessage msg) { + final Quorum<?, ?> quorum = member.getQuorum(); - // Use size and checksum from real IHAWriteMessage. - super(msg.getSize(),msg.getChk()); - - this.req = req; // MAY be null; - this.msg = msg; - - } + final IHASendState snd = new HASendState(messageId.incrementAndGet(), + serviceId/* originalSenderId */, serviceId/* senderId */, + quorum.token(), quorum.replicationFactor()); + return snd; + } /* @@ -1214,7 +1206,8 @@ lock(); try { - ft = new FutureTask<Void>(new RobustReplicateTask(req, msg, b)); + ft = new FutureTask<Void>(new RobustReplicateTask(req, + newSendState(), msg, b)); } finally { @@ -1243,6 +1236,11 @@ private final IHASyncRequest req; /** + * Metadata about the state of the sender for this message. + */ + private final IHASendState snd; + + /** * The {@link IHAWriteMessage}. */ private final IHAWriteMessage msg; @@ -1265,10 +1263,14 @@ private final long quorumToken; public RobustReplicateTask(final IHASyncRequest req, - final IHAWriteMessage msg, final ByteBuffer b) { + final IHASendState snd, final IHAWriteMessage msg, + final ByteBuffer b) { // Note: [req] MAY be null. + if (snd == null) + throw new IllegalArgumentException(); + if (msg == null) throw new IllegalArgumentException(); @@ -1277,6 +1279,8 @@ this.req = req; + this.snd = snd; + this.msg = msg; this.b = b; @@ -1467,6 +1471,7 @@ * at com.bigdata.ha.pipeline.HAReceiveService.run(HAReceiveService.java:431) * </pre> */ + @Override public Void call() throws Exception { final long beginNanos = System.nanoTime(); @@ -1549,7 +1554,7 @@ final ByteBuffer b = this.b.duplicate(); - new SendBufferTask<S>(member, quorumToken, req, msg, b, + new SendBufferTask<S>(member, quorumToken, req, snd, msg, b, downstream, sendService, sendLock).call(); return; @@ -1674,6 +1679,7 @@ private final QuorumMember<S> member; private final long token; // member MUST remain leader for token. private final IHASyncRequest req; + private final IHASendState snd; private final IHAWriteMessage msg; private final ByteBuffer b; private final PipelineState<S> downstream; @@ -1681,13 +1687,15 @@ private final Lock sendLock; public SendBufferTask(final QuorumMember<S> member, final long token, - final IHASyncRequest req, final IHAWriteMessage msg, - final ByteBuffer b, final PipelineState<S> downstream, + final IHASyncRequest req, final IHASendState snd, + final IHAWriteMessage msg, final ByteBuffer b, + final PipelineState<S> downstream, final HASendService sendService, final Lock sendLock) { this.member = member; this.token = token; this.req = req; // Note: MAY be null. + this.snd = snd; this.msg = msg; this.b = b; this.downstream = downstream; @@ -1696,6 +1704,7 @@ } + @Override public Void call() throws Exception { /* @@ -1723,13 +1732,13 @@ ExecutionException, IOException { // Get Future for send() outcome on local service. - final Future<Void> futSnd = sendService.send(b); + final Future<Void> futSnd = sendService.send(b, snd.getMarker()); try { // Get Future for receive outcome on the remote service (RMI). final Future<Void> futRec = downstream.service - .receiveAndReplicate(req, msg); + .receiveAndReplicate(req, snd, msg); try { @@ -1780,7 +1789,8 @@ @Override public Future<Void> receiveAndReplicate(final IHASyncRequest req, - final IHAWriteMessage msg) throws IOException { + final IHASendState snd, final IHAWriteMessage msg) + throws IOException { /* * FIXME We should probably pass the quorum token through from the @@ -1837,7 +1847,7 @@ */ ft = new FutureTask<Void>(new ReceiveTask<S>(member, token, - req, msg, b, receiveService)); + req, snd, msg, b, receiveService)); // try { // @@ -1862,7 +1872,8 @@ */ ft = new FutureTask<Void>(new ReceiveAndReplicateTask<S>( - member, token, req, msg, b, downstream, receiveService)); + member, token, req, snd, msg, b, downstream, + receiveService)); } @@ -1891,6 +1902,7 @@ private final QuorumMember<S> member; private final long token; private final IHASyncRequest req; + private final IHASendState snd; private final IHAWriteMessage msg; private final ByteBuffer b; private final HAReceiveService<HAMessageWrapper> receiveService; @@ -1898,6 +1910,7 @@ public ReceiveTask(final QuorumMember<S> member, final long token, final IHASyncRequest req, + final IHASendState snd, final IHAWriteMessage msg, final ByteBuffer b, final HAReceiveService<HAMessageWrapper> receiveService ) { @@ -1905,16 +1918,18 @@ this.member = member; this.token = token; this.req = req; // Note: MAY be null. + this.snd = snd; this.msg = msg; this.b = b; this.receiveService = receiveService; } + @Override public Void call() throws Exception { - // wrap the messages together. + // wrap the messages together. final HAMessageWrapper wrappedMsg = new HAMessageWrapper( - req, msg); + req, snd, msg); // Get Future for send() outcome on local service. final Future<Void> futSnd = receiveService.receiveData(wrappedMsg, @@ -1957,6 +1972,7 @@ private final QuorumMember<S> member; private final long token; private final IHASyncRequest req; + private final IHASendState snd; private final IHAWriteMessage msg; private final ByteBuffer b; private final PipelineState<S> downstream; @@ -1964,6 +1980,7 @@ public ReceiveAndReplicateTask(final QuorumMember<S> member, final long token, final IHASyncRequest req, + final IHASendState snd, final IHAWriteMessage msg, final ByteBuffer b, final PipelineState<S> downstream, final HAReceiveService<HAMessageWrapper> receiveService) { @@ -1971,17 +1988,19 @@ this.member = member; this.token = token; this.req = req; // Note: MAY be null. + this.snd = snd; this.msg = msg; this.b = b; this.downstream = downstream; this.receiveService = receiveService; } + @Override public Void call() throws Exception { // wrap the messages together. final HAMessageWrapper wrappedMsg = new HAMessageWrapper( - req, msg); + req, snd, msg); // Get Future for send() outcome on local service. final Future<Void> futSnd = receiveService.receiveData(wrappedMsg, @@ -1992,7 +2011,7 @@ // Get future for receive outcome on the remote // service. final Future<Void> futRec = downstream.service - .receiveAndReplicate(req, msg); + .receiveAndReplicate(req, snd, msg); try { Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumServiceBase.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumServiceBase.java 2013-12-11 16:31:29 UTC (rev 7635) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumServiceBase.java 2013-12-12 23:38:47 UTC (rev 7636) @@ -36,6 +36,7 @@ import org.apache.log4j.Logger; +import com.bigdata.ha.msg.IHASendState; import com.bigdata.ha.msg.IHASyncRequest; import com.bigdata.ha.msg.IHAWriteMessage; import com.bigdata.journal.AbstractJournal; @@ -233,10 +234,11 @@ @Override public Future<Void> receiveAndReplicate(final IHASyncRequest req, - final IHAWriteMessage msg) throws IOException { + final IHASendState snd, final IHAWriteMessage msg) + throws IOException { + + return pipelineImpl.receiveAndReplicate(req, snd, msg); - return pipelineImpl.receiveAndReplicate(req, msg); - } @Override Added: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/HAMessageWrapper.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/HAMessageWrapper.java (rev 0) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/HAMessageWrapper.java 2013-12-12 23:38:47 UTC (rev 7636) @@ -0,0 +1,84 @@ +/** + +Copyright (C) SYSTAP, LLC 2006-2010. All rights reserved. + +Contact: + SYSTAP, LLC + 4501 Tower Road + Greensboro, NC 27410 + lic...@bi... + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; version 2 of the License. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ +package com.bigdata.ha.msg; + +import com.bigdata.ha.pipeline.HAReceiveService; + +/** + * Glue class wraps the {@link IHAWriteMessage} and the {@link IHALogRequest} + * message and exposes the requires {@link IHAMessage} interface to the + * {@link HAReceiveService}. This class is never persisted. It just let's us + * handshake with the {@link HAReceiveService} and get back out the original + * {@link IHAWriteMessage} as well as the optional {@link IHALogRequest} + * message. + * + * @author <a href="mailto:tho...@us...">Bryan Thompson</a> + */ +public class HAMessageWrapper extends HAWriteMessageBase implements + IHAMessageWrapper { + + private static final long serialVersionUID = 1L; + + private final IHASyncRequest req; + private final IHASendState snd; + private final IHAWriteMessageBase msg; + + public HAMessageWrapper(final IHASyncRequest req, final IHASendState snd, + final IHAWriteMessageBase msg) { + + // Use size and checksum from real IHAWriteMessage. + super(msg.getSize(), msg.getChk()); + + this.req = req; // MAY be null; + this.snd = snd; + this.msg = msg; + + } + + @Override + public IHASyncRequest getHASyncRequest() { + return req; + } + + @Override + public IHASendState getHASendState() { + return snd; + } + + @Override + public IHAWriteMessageBase getHAWriteMessage() { + return msg; + } + + /** + * Return the {@link IHASendState#getMarker()} iff there is an associated + * {@link IHASendState} and otherwise <code>null</code>. + */ + public byte[] getMarker() { + + return snd == null ? null : snd.getMarker(); + + } + +} Added: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/HASendState.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/HASendState.java (rev 0) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/HASendState.java 2013-12-12 23:38:47 UTC (rev 7636) @@ -0,0 +1,245 @@ +package com.bigdata.ha.msg; + +import java.io.DataOutput; +import java.io.Externalizable; +import java.io.IOException; +import java.io.ObjectInput; +import java.io.ObjectOutput; +import java.util.UUID; + +import com.bigdata.io.DataOutputBuffer; +import com.bigdata.rawstore.Bytes; + +public class HASendState implements IHASendState, Externalizable { + +// private static final Logger log = Logger.getLogger(HASendState.class); + + private static final long serialVersionUID = 1; + + private long messageId; + private UUID originalSenderId; + private UUID senderId; + private long token; + private int replicationFactor; + + /** + * De-serialization constructor. + */ + public HASendState() { + + } + + public HASendState(final long messageId, final UUID originalSenderId, + final UUID senderId, final long token, final int replicationFactor) { + + if (originalSenderId == null) + throw new IllegalArgumentException(); + + if (senderId == null) + throw new IllegalArgumentException(); + + if (replicationFactor <= 0) + throw new IllegalArgumentException(); + + this.messageId = messageId; + this.originalSenderId = originalSenderId; + this.senderId = senderId; + this.token = token; + this.replicationFactor = replicationFactor; + + } + + @Override + public long getMessageId() { + + return messageId; + + } + + @Override + public UUID getOriginalSenderId() { + + return originalSenderId; + } + + @Override + public UUID getSenderId() { + + return senderId; + } + + @Override + public long getQuorumToken() { + + return token; + + } + + @Override + public int getReplicationFactor() { + + return replicationFactor; + + } + + @Override + public byte[] getMarker() { + + final byte[] a = new byte[MAGIC_SIZE + currentVersionLen]; + + final DataOutputBuffer dob = new DataOutputBuffer(0/* len */, a); + + try { + + dob.writeLong(MAGIC); + + writeExternal2(dob); + + } catch (IOException e) { + + throw new RuntimeException(e); + + } + + return a; + + } + + @Override + public String toString() { + + return super.toString() + "{messageId=" + messageId + + ",originalSenderId=" + originalSenderId + ",senderId=" + + senderId + ",token=" + token + ", replicationFactor=" + + replicationFactor + "}"; + + } + + @Override + public boolean equals(final Object obj) { + + if (this == obj) + return true; + + if (!(obj instanceof IHASendState)) + return false; + + final IHASendState t = (IHASendState) obj; + + return messageId == t.getMessageId() + && originalSenderId.equals(t.getOriginalSenderId()) + && senderId.equals(t.getSenderId()) && token == t.getQuorumToken() + && replicationFactor == t.getReplicationFactor(); + + } + + @Override + public int hashCode() { + + // based on the messageId and the hashCode of the senderId + return ((int) (messageId ^ (messageId >>> 32))) + senderId.hashCode(); + } + + /** + * Magic data only included in the marker. + */ + private static final long MAGIC = 0x13759f98e8363caeL; + private static final int MAGIC_SIZE = Bytes.SIZEOF_LONG; + + private static final transient short VERSION0 = 0x0; + private static final transient int VERSION0_LEN = // + Bytes.SIZEOF_LONG + // messageId + Bytes.SIZEOF_UUID + // originalSenderId + Bytes.SIZEOF_UUID + // senderId + Bytes.SIZEOF_LONG + // token + Bytes.SIZEOF_INT // replicationFactor + ; + + private static final transient short currentVersion = VERSION0; + private static final transient int currentVersionLen = VERSION0_LEN; + + @Override + public void readExternal(final ObjectInput in) throws IOException, + ClassNotFoundException { + + final short version = in.readShort(); + + if (version != VERSION0) + throw new RuntimeException("Bad version for serialization"); + + messageId = in.readLong(); + + originalSenderId = new UUID(// + in.readLong(), /* MSB */ + in.readLong() /* LSB */ + ); + + senderId = new UUID(// + in.readLong(), /* MSB */ + in.readLong() /* LSB */ + ); + + token = in.readLong(); + + replicationFactor = in.readInt(); + + } + + @Override + public void writeExternal(final ObjectOutput out) throws IOException { + + writeExternal2(out); + + } + + private void writeExternal2(final DataOutput out) throws IOException { + + out.writeShort(currentVersion); + + out.writeLong(messageId); + + out.writeLong(originalSenderId.getMostSignificantBits()); + out.writeLong(originalSenderId.getLeastSignificantBits()); + + out.writeLong(senderId.getMostSignificantBits()); + out.writeLong(senderId.getLeastSignificantBits()); + + out.writeLong(token); + + out.writeInt(replicationFactor); + + } + + // static final private int MARKER_SIZE = 8; + // + // /** + // * Unique marker generation with JVM wide random number generator. + // * + // * @return A "pretty unique" marker. + // */ + // private byte[] genMarker() { + // + // final byte[] token = new byte[MARKER_SIZE]; + // + // while (!unique1(token)) { + // r.nextBytes(token); + // } + // + // return token; + // } + // + // /** + // * Checks that the first byte is not repeated in the remaining bytes, this + // * simplifies search for the token in the input stream. + // */ + // static private boolean unique1(final byte[] bytes) { + // final byte b = bytes[0]; + // for (int t = 1; t < bytes.length; t++) { + // if (bytes[t] == b) + // return false; + // } + // + // return true; + // } + +} Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/HAWriteMessage.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/HAWriteMessage.java 2013-12-11 16:31:29 UTC (rev 7635) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/HAWriteMessage.java 2013-12-12 23:38:47 UTC (rev 7636) @@ -159,6 +159,7 @@ return compressorKey; } + @Override public String toString() { return getClass().getName() // @@ -347,7 +348,9 @@ * @return */ public static boolean isDataCompressed() { - return compressData; + + return compressData; + } @Override @@ -375,6 +378,7 @@ } + @Override public void readExternal(final ObjectInput in) throws IOException, ClassNotFoundException { @@ -414,6 +418,7 @@ firstOffset = in.readLong(); } + @Override public void writeExternal(final ObjectOutput out) throws IOException { super.writeExternal(out); if (currentVersion >= VERSION1 && uuid != null) { @@ -469,6 +474,7 @@ // return compressor.compress(buffer); // } + @Override public ByteBuffer expand(final ByteBuffer buffer) { final String compressorKey = getCompressorKey(); Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/HAWriteMessageBase.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/HAWriteMessageBase.java 2013-12-11 16:31:29 UTC (rev 7635) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/HAWriteMessageBase.java 2013-12-12 23:38:47 UTC (rev 7636) @@ -63,15 +63,15 @@ * The Alder32 checksum of the bytes to be transfered. */ public HAWriteMessageBase(final int sze, final int chk) { - + if (sze <= 0) throw new IllegalArgumentException(); this.sze = sze; this.chk = chk; - - } + + } /** * Deserialization constructor. @@ -97,7 +97,8 @@ return chk; } - + + @Override public String toString() { return super.toString() + "{size=" + sze + ",chksum=" + chk + "}"; @@ -131,6 +132,7 @@ private static final transient short currentVersion = VERSION0; + @Override public void readExternal(final ObjectInput in) throws IOException, ClassNotFoundException { @@ -145,6 +147,7 @@ } + @Override public void writeExternal(final ObjectOutput out) throws IOException { out.writeShort(currentVersion); @@ -152,7 +155,7 @@ out.writeInt(sze); out.writeInt(chk); - + } } Added: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/IHAMessageWrapper.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/IHAMessageWrapper.java (rev 0) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/IHAMessageWrapper.java 2013-12-12 23:38:47 UTC (rev 7636) @@ -0,0 +1,59 @@ +/** + +Copyright (C) SYSTAP, LLC 2006-2010. All rights reserved. + +Contact: + SYSTAP, LLC + 4501 Tower Road + Greensboro, NC 27410 + lic...@bi... + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; version 2 of the License. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ +package com.bigdata.ha.msg; + +import com.bigdata.ha.pipeline.HAReceiveService; + +/** + * Glue interface wraps the {@link IHALogRequest}, {@link IHASendState}, and + * {@link IHAWriteMessage} interfaces exposes the requires {@link IHAMessage} + * interface to the {@link HAReceiveService}. This class is never persisted (it + * does NOT get written into the HALog files). It just let's us handshake with + * the {@link HAReceiveService} and get back out the original + * {@link IHAWriteMessage} as well as the optional {@link IHALogRequest} + * message. + * + * @author <a href="mailto:tho...@us...">Bryan Thompson</a> + */ +public interface IHAMessageWrapper { + + /** + * Return the optional {@link IHASyncRequest}. When available, this provides + * information about the service request that resulted in the transmission + * of the payload along the pipeline. + */ + IHASyncRequest getHASyncRequest(); + + /** + * Return information about the state of the sending service. + */ + IHASendState getHASendState(); + + /** + * Return the message that describes the payload that will be replicated + * along the pipeline. + */ + IHAWriteMessageBase getHAWriteMessage(); + +} Added: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/IHASendState.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/IHASendState.java (rev 0) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/msg/IHASendState.java 2013-12-12 23:38:47 UTC (rev 7636) @@ -0,0 +1,71 @@ +/** + +Copyright (C) SYSTAP, LLC 2006-2010. All rights reserved. + +Contact: + SYSTAP, LLC + 4501 Tower Road + Greensboro, NC 27410 + lic...@bi... + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; version 2 of the License. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ +package com.bigdata.ha.msg; + +import java.io.Serializable; +import java.util.UUID; + +/** + * Interface for the state of the sender of an {@link IHAMessage}. + * + * @author <a href="mailto:tho...@us...">Bryan Thompson</a> + */ +public interface IHASendState extends Serializable { + + /** + * A unique (one-up) message sequence identifier for the messages from the + * sender. This identifier may be used to verify that the bytes available + * from the replication stream are associated with the designed payload. + */ + long getMessageId(); + + /** + * The {@link UUID} of the originating service. This may be used to verify + * that a message was sourced the expected quorum leader. + */ + UUID getOriginalSenderId(); + + /** + * The {@link UUID} of the sending service. This may be used to verify that + * a message was sourced the expected upstream service. + */ + UUID getSenderId(); + + /** + * The current quorum token on the sender. + */ + long getQuorumToken(); + + /** + * The current replication factor on the sender. + */ + int getReplicationFactor(); + + /** + * A byte[] marker that must prefix the message payload, needed to skip + * stale data from failed read tasks. + */ + byte[] getMarker(); + +} Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HAReceiveService.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HAReceiveService.java 2013-12-11 16:31:29 UTC (rev 7635) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HAReceiveService.java 2013-12-12 23:38:47 UTC (rev 7636) @@ -51,7 +51,9 @@ import org.apache.log4j.Logger; +import com.bigdata.btree.BytesUtil; import com.bigdata.ha.QuorumPipelineImpl; +import com.bigdata.ha.msg.HAMessageWrapper; import com.bigdata.ha.msg.IHAMessage; import com.bigdata.ha.msg.IHASyncRequest; import com.bigdata.ha.msg.IHAWriteMessage; @@ -73,7 +75,7 @@ * @author Martyn Cutcher * @author <a href="mailto:tho...@us...">Bryan Thompson</a> */ -public class HAReceiveService<M extends IHAWriteMessageBase> extends Thread { +public class HAReceiveService<M extends HAMessageWrapper> extends Thread { private static final Logger log = Logger .getLogger(HAReceiveService.class); @@ -225,6 +227,7 @@ /* * Note: toString() implementation is non-blocking. */ + @Override public String toString() { return super.toString() + "{addrSelf=" + addrSelf + ", addrNext=" @@ -725,7 +728,7 @@ * <p> * report the #of payloads. */ - static private class ReadTask<M extends IHAWriteMessageBase> implements + static private class ReadTask<M extends HAMessageWrapper> implements Callable<Void> { private final ServerSocketChannel server; @@ -983,18 +986,25 @@ private void doReceiveAndReplicate(final Client client) throws Exception { - /** - * The first cause if downstream replication fails. We make a note - * of this first cause, continue to drain the payload, and then - * rethrow the first cause once the payload has been fully drained. - * This is necessary to ensure that the socket channel does not have - * partial data remaining from an undrained payload. - * - * @see <a - * href="https://sourceforge.net/apps/trac/bigdata/ticket/724" - * > HA wire pulling and sure kill testing </a> - */ - Throwable downstreamFirstCause = null; +// /** +// * The first cause if downstream replication fails. We make a note +// * of this first cause, continue to drain the payload, and then +// * rethrow the first cause once the payload has been fully drained. +// * This is necessary to ensure that the socket channel does not have +// * partial data remaining from an undrained payload. +// * +// * @see <a +// * href="https://sourceforge.net/apps/trac/bigdata/ticket/724" +// * > HA wire pulling and sure kill testing </a> +// * +// * Note: It appears that attempting to drain the +// * payload is risky since there are a variety of ways in which +// * the process might be terminated. It seems to be safer to +// * drain the socket channel until we reach a marker that gives +// * us confidence that we are at the payload for the message +// * that is being processed. +// */ +// Throwable downstreamFirstCause = null; /* * We should now have parameters ready in the WriteMessage and can @@ -1012,6 +1022,9 @@ // for debug retain number of low level reads int reads = 0; + final DrainToMarkerUtil drainUtil = message.getHASendState() != null ? new DrainToMarkerUtil( + message.getHASendState().getMarker(), client) : null; + while (rem > 0 && !EOS) { // block up to the timeout. @@ -1070,9 +1083,16 @@ while (iter.hasNext()) { + // Check for termination. + client.checkFirstCause(); + iter.next(); iter.remove(); + if (!drainUtil.foundMarker()) { + continue; + } + final int rdlen = client.client.read(localBuffer); if (log.isTraceEnabled()) @@ -1098,17 +1118,17 @@ callback.incReceive(message, reads, rdlen, rem); } - if (downstreamFirstCause == null) { - try { +// if (downstreamFirstCause == null) { +// try { forwardReceivedBytes(client, rdlen); - } catch (ExecutionException ex) { - log.error( - "Downstream replication failure" - + ": will drain payload and then rethrow exception: rootCause=" - + ex, ex); - downstreamFirstCause = ex; - } - } +// } catch (ExecutionException ex) { +// log.error( +// "Downstream replication failure" +// + ": will drain payload and then rethrow exception: rootCause=" +// + ex, ex); +// downstreamFirstCause = ex; +// } +// } } // while(itr.hasNext()) @@ -1134,28 +1154,31 @@ + ", actual=" + (int) chk.getValue()); } - if (downstreamFirstCause != null) { - - /** - * Replication to the downstream service failed. The payload has - * been fully drained. This ensures that we do not leave part of - * the payload in the upstream socket channel. We now wrap and - * rethrow the root cause of the downstream failure. The leader - * will handle this by forcing the remove of the downstream - * service and then re-replicating the payload. - * - * @see <a - * href="https://sourceforge.net/apps/trac/bigdata/ticket/724" - * > HA wire pulling and sure kill testing </a> - */ +// if (downstreamFirstCause != null) { +// +// /** +// * Replication to the downstream service failed. The payload has +// * been fully drained. This ensures that we do not leave part of +// * the payload in the upstream socket channel. We now wrap and +// * rethrow the root cause of the downstream failure. The leader +// * will handle this by forcing the remove of the downstream +// * service and then re-replicating the payload. +// * +// * @see <a +// * href="https://sourceforge.net/apps/trac/bigdata/ticket/724" +// * > HA wire pulling and sure kill testing </a> +// */ +// +// throw new RuntimeException( +// "Downstream replication failure: msg=" + message +// + ", ex=" + downstreamFirstCause, +// downstreamFirstCause); +// +// } + + // Check for termination. + client.checkFirstCause(); - throw new RuntimeException( - "Downstream replication failure: msg=" + message - + ", ex=" + downstreamFirstCause, - downstreamFirstCause); - - } - if (callback != null) { /* @@ -1173,7 +1196,7 @@ } // call() /** - * Now forward the most recent transfer bytes downstream. + * Forward the most recent transfer bytes downstream. * <p> * * Note: [addrNext] is final. If the downstream address is changed, then @@ -1229,107 +1252,123 @@ } // Check for termination. client.checkFirstCause(); - // Send and await Future. - sendService.send(out).get(); + /* + * Send and await Future. If this is the first chunk of a + * payload and a marker exists, then send the marker as + * well. + */ + sendService + .send(out, + out.position() == 0 + && message.getHASendState() != null ? message + .getHASendState().getMarker() + : null).get(); } break; // break out of the inner while loop. } // while(true) } - -// private void ack(final Client client) throws IOException { -// -// if (log.isTraceEnabled()) -// log.trace("Will ACK"); -// -// ack(client.client, HASendService.ACK); -// -// if (log.isTraceEnabled()) -// log.trace("Did ACK"); -// -// } -// -// private void nack(final Client client) throws IOException { -// -// if (log.isTraceEnabled()) -// log.trace("Will NACK"); -// -// ack(client.client, HASendService.NACK); -// -// if (log.isTraceEnabled()) -// log.trace("Did NACK"); -// -// } -// -// /** -// * ACK/NACK the payload. -// * -// * @param client -// * @throws IOException -// */ -// private void ack(final SocketChannel client, final byte ret) -// throws IOException { -// -// // FIXME optimize. -// final ByteBuffer b = ByteBuffer.wrap(new byte[] { ret /* ACK */}); -// -// // The #of bytes to transfer. -// final int remaining = b.remaining(); -// -//// if (log.isTraceEnabled()) -//// log.trace("Will send " + remaining + " bytes"); -// -//// try { -// -// int nwritten = 0; -// -// while (nwritten < remaining) { -// -// /* -// * Write the data. Depending on the channel, will either -// * block or write as many bytes as can be written -// * immediately (this latter is true for socket channels in a -// * non-blocking mode). IF it blocks, should block until -// * finished or until this thread is interrupted, e.g., by -// * shutting down the thread pool on which it is running. -// * -// * Note: If the SocketChannel is closed by an interrupt, -// * then the send request for the [data] payload will fail. -// * However, the SocketChannel will be automatically reopened -// * for the next request (unless the HASendService has been -// * terminated). -// */ -// -// final int nbytes = client.write(b); -// -// nwritten += nbytes; -// -//// if (log.isTraceEnabled()) -//// log.trace("Sent " + nbytes + " bytes with " + nwritten -//// + " of out " + remaining + " written so far"); -// -// } -// return; -// -//// while (client.isOpen()) { -//// -//// if (client.write(b) > 0) { -//// -//// // Sent (N)ACK byte. -//// return; -//// -//// } -//// -//// } -// -//// // channel is closed. -//// throw new AsynchronousCloseException(); -// -// } - + } // class ReadTask /** + * Helper class to drain bytes from the upstream socket until we encounter a + * marker in the stream that immediately proceeds the desired payload. + * + * @author <a href="mailto:mar...@us...">Martyn + * Cutcher</a> + * + * @see <a href="https://sourceforge.net/apps/trac/bigdata/ticket/724" > HA + * wire pulling and sure kill testing </a> + */ + static private class DrainToMarkerUtil { + + final private byte[] marker; + final private byte[] markerBuffer; + final private ByteBuffer markerBB; + final private Client client; + + private int markerIndex = 0; + private int nmarkerreads = 0; + private int nmarkerbytematches = 0; + + DrainToMarkerUtil(final byte[] marker, final Client client) { + this.marker = marker; + this.markerBuffer = marker == null ? null : new byte[marker.length]; + this.markerBB = marker == null ? null : ByteBuffer + .wrap(markerBuffer); + this.client = client; + + if (log.isDebugEnabled()) + log.debug("Receive token: " + BytesUtil.toHexString(marker)); + + } + + /** + * Note that the logic for finding the token bytes depends on the first + * byte in the token being unique! + * <p> + * We have to be a bit clever to be sure we do not read beyond the token + * and therefore complicate the reading into the localBuffer. + * <p> + * This is optimized for the normal case where the marker is read as + * from the next bytes from the stream. In the worst case scenario this + * could read large amounts of data only a few bytes at a time, however + * this is not in reality a significant overhead. + */ + boolean foundMarker() throws IOException { + + if (log.isDebugEnabled()) + log.debug("Looking for token, " + BytesUtil.toHexString(marker) + + ", reads: " + nmarkerreads); + + while (markerIndex < marker.length) { + + final int remtok = marker.length - markerIndex; + markerBB.limit(remtok); + markerBB.position(0); + + final int rdLen = client.client.read(markerBB); + for (int i = 0; i < rdLen; i++) { + if (markerBuffer[i] != marker[markerIndex]) { + if (nmarkerreads < 2) + log.warn("TOKEN MISMATCH"); + markerIndex = 0; + if (markerBuffer[i] == marker[markerIndex]) { + markerIndex++; + } + } else { + markerIndex++; + nmarkerbytematches++; + } + } + + nmarkerreads++; + if (nmarkerreads % 10000 == 0) { + if (log.isDebugEnabled()) + log.debug("...still looking, reads: " + nmarkerreads); + } + + } + + if (markerIndex != marker.length) { // not sufficient data ready + if (log.isDebugEnabled()) + log.debug("Not found token yet!"); + return false; + } else { + if (log.isDebugEnabled()) + log.debug("Found token after " + nmarkerreads + + " token reads and " + nmarkerbytematches + + " byte matches"); + + return true; + } + + } + + } + + /** * Receive data into the caller's buffer as described by the caller's * message. * @@ -1408,21 +1447,6 @@ public interface IHAReceiveCallback<M extends IHAWriteMessageBase> { /** - * Hook invoked once a buffer has been received. - * - * @param msg - * The message. - * @param data - * The buffer containing the data. The position() will be - * ZERO (0). The limit() will be the #of bytes available. The - * implementation MAY have side effects on the buffer state - * (position, limit, etc). - * - * @throws Exception - */ - void callback(M msg, ByteBuffer data) throws Exception; - - /** * Notify that some payload bytes have been incrementally received for * an {@link IHAMessage}. This is invoked each time some data has been * read from the upstream socket. @@ -1441,6 +1465,22 @@ * @throws Exception */ void incReceive(M msg, int nreads, int rdlen, int rem) throws Exception; + + /** + * Hook invoked once a buffer has been received. + * + * @param msg + * The message. + * @param data + * The buffer containing the data. The position() will be + * ZERO (0). The limit() will be the #of bytes available. The + * implementation MAY have side effects on the buffer state + * (position, limit, etc). + * + * @throws Exception + */ + void callback(M msg, ByteBuffer data) throws Exception; + } /** Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HASendService.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HASendService.java 2013-12-11 16:31:29 UTC (rev 7635) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HASendService.java 2013-12-12 23:38:47 UTC (rev 7636) @@ -287,6 +287,10 @@ * * @param buffer * The buffer. + * @param marker + * A marker that will be used to prefix the payload for the + * message in the write replication socket stream. The marker is + * used to ensure synchronization when reading on the stream. * * @return The {@link Future} which can be used to await the outcome of this * operation. @@ -301,8 +305,8 @@ * @todo throws IOException if the {@link SocketChannel} was not open and * could not be opened. */ - public Future<Void> send(final ByteBuffer buffer) { - + public Future<Void> send(final ByteBuffer buffer, final byte[] marker) { + if (buffer == null) throw new IllegalArgumentException(); @@ -320,10 +324,9 @@ // reopenChannel(); - return tmp.submit(newIncSendTask(buffer.asReadOnlyBuffer())); + return tmp.submit(newIncSendTask(buffer.asReadOnlyBuffer(), marker)); } - /** * A series of timeouts used when we need to re-open the * {@link SocketChannel}. @@ -422,13 +425,17 @@ * * @param buffer * The buffer whose data are to be sent. + * @param marker + * A marker that will be used to prefix the payload for the + * message in the write replication socket stream. The marker is + * used to ensure synchronization when reading on the stream. * * @return The task which will send the data to the configured * {@link InetSocketAddress}. */ - protected Callable<Void> newIncSendTask(final ByteBuffer buffer) { + protected Callable<Void> newIncSendTask(final ByteBuffer buffer, final byte[] marker) { - return new IncSendTask(buffer); + return new IncSendTask(buffer, marker); } @@ -485,25 +492,21 @@ */ protected /*static*/ class IncSendTask implements Callable<Void> { -// private final SocketChannel socketChannel; - private final ByteBuffer data; + private final ByteBuffer data; + private final byte[] marker; - public IncSendTask(/*final SocketChannel socketChannel, */final ByteBuffer data) { + public IncSendTask(final ByteBuffer data, final byte[] marker) { -// if (socketChannel == null) -// throw new IllegalArgumentException(); + if (data == null) + throw new IllegalArgumentException(); - if (data == null) - throw new IllegalArgumentException(); + this.data = data; + this.marker = marker; + } -// this.socketChannel = socketChannel; - - this.data = data; + @Override + public Void call() throws Exception { - } - - public Void call() throws Exception { - // defer until we actually run. final SocketChannel socketChannel = reopenChannel(); @@ -521,10 +524,22 @@ try { - int nwritten = 0; + int nmarker = 0; // #of marker bytes written. + int nwritten = 0; // #of payload bytes written. + + final ByteBuffer markerBB = marker != null ? ByteBuffer + .wrap(marker) : null; while (nwritten < remaining) { + + if (marker != null && nmarker < marker.length) { + + nmarker += socketChannel.write(markerBB); + continue; + + } + /* * Write the data. Depending on the channel, will either * block or write as many bytes as can be written Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/journal/AbstractJournal.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/journal/AbstractJournal.java 2013-12-11 16:31:29 UTC (rev 7635) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/journal/AbstractJournal.java 2013-12-12 23:38:47 UTC (rev 7636) @@ -132,6 +132,7 @@ import com.bigdata.ha.msg.IHARemoteRebuildRequest; import com.bigdata.ha.msg.IHARootBlockRequest; import com.bigdata.ha.msg.IHARootBlockResponse; +import com.bigdata.ha.msg.IHASendState; import com.bigdata.ha.msg.IHASendStoreResponse; import com.bigdata.ha.msg.IHASnapshotDigestRequest; import ... [truncated message content] |
From: <mar...@us...> - 2013-12-13 10:45:03
|
Revision: 7640 http://bigdata.svn.sourceforge.net/bigdata/?rev=7640&view=rev Author: martyncutcher Date: 2013-12-13 10:44:56 +0000 (Fri, 13 Dec 2013) Log Message: ----------- Intermediate implementation of PipelineException and pipeline propagation leading to forceRemoveService invocation on leader Modified Paths: -------------- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHA3JustKills.java Added Paths: ----------- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/PipelineException.java Added: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/PipelineException.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/PipelineException.java (rev 0) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/PipelineException.java 2013-12-13 10:44:56 UTC (rev 7640) @@ -0,0 +1,56 @@ +/** + +Copyright (C) SYSTAP, LLC 2006-2013. All rights reserved. + +Contact: + SYSTAP, LLC + 4501 Tower Road + Greensboro, NC 27410 + lic...@bi... + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; version 2 of the License. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ + +package com.bigdata.ha; + +import java.util.UUID; + +/** + * PipelineException is thrown from RMI calls to communicate + * the root cause of a pipeline problem. The caller is then able + * to take action: for example to remove the problem service + * from the quorum. + */ +public class PipelineException extends RuntimeException { + + /** + * Generated ID + */ + private static final long serialVersionUID = 8019938954269914574L; + + /** The UUID of the service that could not be reached. */ + private final UUID serviceId; + + public PipelineException(final UUID serviceId, final Throwable t) { + super(t); + + this.serviceId = serviceId; + } + + /** Return the UUID of the service that could not be reached. */ + public UUID getProblemServiceId() { + return serviceId; + } + +} Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java 2013-12-13 09:07:46 UTC (rev 7639) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java 2013-12-13 10:44:56 UTC (rev 7640) @@ -1729,56 +1729,91 @@ } private void doRunWithLock() throws InterruptedException, - ExecutionException, IOException { + ExecutionException, IOException { - // Get Future for send() outcome on local service. - final Future<Void> futSnd = sendService.send(b, snd.getMarker()); + try { + // Get Future for send() outcome on local service. + final Future<Void> futSnd = sendService + .send(b, snd.getMarker()); - try { + try { - // Get Future for receive outcome on the remote service (RMI). - final Future<Void> futRec = downstream.service - .receiveAndReplicate(req, snd, msg); + // Get Future for receive outcome on the remote service + // (RMI). + final Future<Void> futRec = downstream.service + .receiveAndReplicate(req, snd, msg); - try { + try { - /* - * Await the Futures, but spend more time waiting on the - * local Future and only check the remote Future every - * second. Timeouts are ignored during this loop. - */ - while (!futSnd.isDone() && !futRec.isDone()) { - /* - * Make sure leader's quorum token remains valid for ALL - * writes. - */ - member.assertLeader(token); - try { - futSnd.get(1L, TimeUnit.SECONDS); - } catch (TimeoutException ignore) { - } - try { - futRec.get(10L, TimeUnit.MILLISECONDS); - } catch (TimeoutException ignore) { - } - } - futSnd.get(); - futRec.get(); + /* + * Await the Futures, but spend more time waiting on the + * local Future and only check the remote Future every + * second. Timeouts are ignored during this loop. + */ + while (!futSnd.isDone() && !futRec.isDone()) { + /* + * Make sure leader's quorum token remains valid for + * ALL writes. + */ + member.assertLeader(token); + try { + futSnd.get(1L, TimeUnit.SECONDS); + } catch (TimeoutException ignore) { + } + try { + futRec.get(10L, TimeUnit.MILLISECONDS); + } catch (TimeoutException ignore) { + } + } + futSnd.get(); + futRec.get(); - } finally { - if (!futRec.isDone()) { - // cancel remote Future unless done. - futRec.cancel(true/* mayInterruptIfRunning */); - } - } + } finally { + if (!futRec.isDone()) { + // cancel remote Future unless done. + futRec.cancel(true/* mayInterruptIfRunning */); + } + } - } finally { - // cancel the local Future. - futSnd.cancel(true/* mayInterruptIfRunning */); - } + } finally { + // cancel the local Future. + futSnd.cancel(true/* mayInterruptIfRunning */); + } - } - + } catch (Throwable t) { + // check inner cause for downstream PipelineException + final PipelineException pe = (PipelineException) InnerCause + .getInnerCause(t, PipelineException.class); + final UUID problemService; + if (pe != null) { + // throw pe; // throw it upstream - already should have been + // handled + problemService = pe.getProblemServiceId(); + } else { + final UUID[] priorAndNext = member.getQuorum() + .getPipelinePriorAndNext(member.getServiceId()); + problemService = priorAndNext[1]; + } + + // determine next pipeline service id + log.warn("Problem with downstream service: " + problemService, + t); + + // Carry out remedial work directly - BAD + log.error("Really need to remove service " + problemService); + + try { + member.getActor().forceRemoveService(problemService); + } catch (Exception e) { + log.warn("Problem on node removal", e); + + throw new RuntimeException(e); + } + + throw new PipelineException(problemService, t); + + } + } } /** @@ -1996,69 +2031,81 @@ } @Override - public Void call() throws Exception { + public Void call() throws Exception { - // wrap the messages together. - final HAMessageWrapper wrappedMsg = new HAMessageWrapper( - req, snd, msg); + // wrap the messages together. + final HAMessageWrapper wrappedMsg = new HAMessageWrapper(req, snd, + msg); - // Get Future for send() outcome on local service. - final Future<Void> futSnd = receiveService.receiveData(wrappedMsg, - b); + // Get Future for send() outcome on local service. + final Future<Void> futSnd = receiveService.receiveData(wrappedMsg, + b); - try { + try { + try { - // Get future for receive outcome on the remote - // service. - final Future<Void> futRec = downstream.service - .receiveAndReplicate(req, snd, msg); + // Get future for receive outcome on the remote + // service. + final Future<Void> futRec = downstream.service + .receiveAndReplicate(req, snd, msg); - try { + try { - /* - * Await the Futures, but spend more time - * waiting on the local Future and only check - * the remote Future every second. Timeouts are - * ignored during this loop. - */ - while (!futSnd.isDone() && !futRec.isDone()) { - /* - * The token must remain valid, even if this service is - * not joined with the met quorum. If fact, services - * MUST replicate writes regardless of whether or not - * they are joined with the met quorum, but only while - * there is a met quorum. - */ - member.getQuorum().assertQuorum(token); - try { - futSnd.get(1L, TimeUnit.SECONDS); - } catch (TimeoutException ignore) { - } - try { - futRec.get(10L, TimeUnit.MILLISECONDS); - } catch (TimeoutException ignore) { - } - } - futSnd.get(); - futRec.get(); + /* + * Await the Futures, but spend more time waiting on the + * local Future and only check the remote Future every + * second. Timeouts are ignored during this loop. + */ + while (!futSnd.isDone() && !futRec.isDone()) { + /* + * The token must remain valid, even if this service + * is not joined with the met quorum. If fact, + * services MUST replicate writes regardless of + * whether or not they are joined with the met + * quorum, but only while there is a met quorum. + */ + member.getQuorum().assertQuorum(token); + try { + futSnd.get(1L, TimeUnit.SECONDS); + } catch (TimeoutException ignore) { + } + try { + futRec.get(10L, TimeUnit.MILLISECONDS); + } catch (TimeoutException ignore) { + } + } + futSnd.get(); + futRec.get(); - } finally { - if (!futRec.isDone()) { - // cancel remote Future unless done. - futRec - .cancel(true/* mayInterruptIfRunning */); - } - } + } finally { + if (!futRec.isDone()) { + // cancel remote Future unless done. + futRec.cancel(true/* mayInterruptIfRunning */); + } + } - } finally { - // cancel the local Future. - futSnd.cancel(true/* mayInterruptIfRunning */); - } + } finally { + // Is it possible that this cancel conflicts with throwing + // the PipelineException? + // cancel the local Future. + futSnd.cancel(true/* mayInterruptIfRunning */); + } + } catch (Throwable t) { + // determine next pipeline service id + // FIXME: should this check for problem from further downstream for + // quorums with > 3 services? + final UUID[] priorAndNext = member.getQuorum() + .getPipelinePriorAndNext(member.getServiceId()); + log.warn("Problem with downstream service: " + priorAndNext[1], + t); - // done - return null; - } + throw new PipelineException(priorAndNext[1], t); + } + // done + return null; + } + } /** Modified: branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHA3JustKills.java =================================================================== --- branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHA3JustKills.java 2013-12-13 09:07:46 UTC (rev 7639) +++ branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHA3JustKills.java 2013-12-13 10:44:56 UTC (rev 7640) @@ -106,7 +106,7 @@ // FIXME: in the face of no implemented error propagation we can explicitly // tell the leader to remove the killed service! - startup.serverA.submit(new ForceRemoveService(getServiceCId()), true).get(); + // startup.serverA.submit(new ForceRemoveService(getServiceCId()), true).get(); awaitPipeline(20, TimeUnit.SECONDS, new HAGlue[] {startup.serverA, startup.serverB}); @@ -171,7 +171,7 @@ kill(startup.serverB); // FIXME: temporary call to explicitly remove the service prior to correct protocol - startup.serverA.submit(new ForceRemoveService(getServiceBId()), true).get(); + // startup.serverA.submit(new ForceRemoveService(getServiceBId()), true).get(); awaitPipeline(10, TimeUnit.SECONDS, new HAGlue[] {startup.serverA, startup.serverC}); @@ -317,8 +317,8 @@ // FIXME: temporary call to explicitly remove the service prior to // correct protocol - startup.serverA.submit(new ForceRemoveService(getServiceBId()), true) - .get(); + // startup.serverA.submit(new ForceRemoveService(getServiceBId()), true) + // .get(); awaitPipeline(10, TimeUnit.SECONDS, new HAGlue[] { startup.serverA, startup.serverC }); @@ -396,8 +396,8 @@ // FIXME: temporary call to explicitly remove the service prior to // correct protocol - startup.serverA.submit(new ForceRemoveService(getServiceCId()), true) - .get(); + // startup.serverA.submit(new ForceRemoveService(getServiceCId()), true) + // .get(); awaitPipeline(10, TimeUnit.SECONDS, new HAGlue[] { startup.serverA, startup.serverB }); @@ -496,8 +496,8 @@ executorService.submit(ft); // FIXME RESYNC_PIPELINE: move into QuorumPipelineImpl. - startup.serverA.submit(new ForceRemoveService(getServiceCId()), true) - .get(); + // startup.serverA.submit(new ForceRemoveService(getServiceCId()), true) + // .get(); awaitPipeline(getZKSessionTimeout() + 5000, TimeUnit.MILLISECONDS, new HAGlue[] { startup.serverA, startup.serverB }); This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |
From: <tho...@us...> - 2013-12-13 16:54:38
|
Revision: 7642 http://bigdata.svn.sourceforge.net/bigdata/?rev=7642&view=rev Author: thompsonbry Date: 2013-12-13 16:54:30 +0000 (Fri, 13 Dec 2013) Log Message: ----------- Sync to Martyn and CI changes to the error handling for pipeline replication and some new unit tests. See #724 Modified Paths: -------------- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HAReceiveService.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HASendService.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/PipelineDownstreamChange.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/PipelineUpstreamChange.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/ha/pipeline/TestHASendAndReceive.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/ha/pipeline/TestHASendAndReceive3Nodes.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHA3JustKills.java Added Paths: ----------- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/AbstractPipelineChangeException.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/AbstractPipelineException.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/ImmediateDownstreamReplicationException.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/NestedPipelineException.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/PipelineImmediateDownstreamReplicationException.java Removed Paths: ------------- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/PipelineException.java Deleted: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/PipelineException.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/PipelineException.java 2013-12-13 11:01:37 UTC (rev 7641) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/PipelineException.java 2013-12-13 16:54:30 UTC (rev 7642) @@ -1,56 +0,0 @@ -/** - -Copyright (C) SYSTAP, LLC 2006-2013. All rights reserved. - -Contact: - SYSTAP, LLC - 4501 Tower Road - Greensboro, NC 27410 - lic...@bi... - -This program is free software; you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation; version 2 of the License. - -This program is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. - -You should have received a copy of the GNU General Public License -along with this program; if not, write to the Free Software -Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA -*/ - -package com.bigdata.ha; - -import java.util.UUID; - -/** - * PipelineException is thrown from RMI calls to communicate - * the root cause of a pipeline problem. The caller is then able - * to take action: for example to remove the problem service - * from the quorum. - */ -public class PipelineException extends RuntimeException { - - /** - * Generated ID - */ - private static final long serialVersionUID = 8019938954269914574L; - - /** The UUID of the service that could not be reached. */ - private final UUID serviceId; - - public PipelineException(final UUID serviceId, final Throwable t) { - super(t); - - this.serviceId = serviceId; - } - - /** Return the UUID of the service that could not be reached. */ - public UUID getProblemServiceId() { - return serviceId; - } - -} Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java 2013-12-13 11:01:37 UTC (rev 7641) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java 2013-12-13 16:54:30 UTC (rev 7642) @@ -57,6 +57,9 @@ import com.bigdata.ha.pipeline.HAReceiveService; import com.bigdata.ha.pipeline.HAReceiveService.IHAReceiveCallback; import com.bigdata.ha.pipeline.HASendService; +import com.bigdata.ha.pipeline.ImmediateDownstreamReplicationException; +import com.bigdata.ha.pipeline.NestedPipelineException; +import com.bigdata.ha.pipeline.PipelineImmediateDownstreamReplicationException; import com.bigdata.io.DirectBufferPool; import com.bigdata.io.IBufferAccess; import com.bigdata.quorum.QCE; @@ -1729,91 +1732,147 @@ } private void doRunWithLock() throws InterruptedException, - ExecutionException, IOException { + ExecutionException, IOException { - try { - // Get Future for send() outcome on local service. - final Future<Void> futSnd = sendService - .send(b, snd.getMarker()); + // Get Future for send() outcome on local service. + final Future<Void> futSnd = sendService.send(b, snd.getMarker()); + try { + try { - try { + // Get Future for receive outcome on the remote service + // (RMI). + final Future<Void> futRec; + try { + futRec = downstream.service.receiveAndReplicate(req, + snd, msg); + } catch (IOException ex) { // RMI error. + throw new ImmediateDownstreamReplicationException(ex); + } - // Get Future for receive outcome on the remote service - // (RMI). - final Future<Void> futRec = downstream.service - .receiveAndReplicate(req, snd, msg); + try { - try { + /* + * Await the Futures, but spend more time waiting on the + * local Future and only check the remote Future every + * second. Timeouts are ignored during this loop. + */ + while (!futSnd.isDone() && !futRec.isDone()) { + /* + * Make sure leader's quorum token remains valid for + * ALL writes. + */ + member.assertLeader(token); + try { + futSnd.get(1L, TimeUnit.SECONDS); + } catch (TimeoutException ignore) { + } + try { + futRec.get(10L, TimeUnit.MILLISECONDS); + } catch (TimeoutException ignore) { + } + } + futSnd.get(); + futRec.get(); - /* - * Await the Futures, but spend more time waiting on the - * local Future and only check the remote Future every - * second. Timeouts are ignored during this loop. - */ - while (!futSnd.isDone() && !futRec.isDone()) { - /* - * Make sure leader's quorum token remains valid for - * ALL writes. - */ - member.assertLeader(token); - try { - futSnd.get(1L, TimeUnit.SECONDS); - } catch (TimeoutException ignore) { - } - try { - futRec.get(10L, TimeUnit.MILLISECONDS); - } catch (TimeoutException ignore) { - } - } - futSnd.get(); - futRec.get(); + } finally { + if (!futRec.isDone()) { + // cancel remote Future unless done. + futRec.cancel(true/* mayInterruptIfRunning */); + } + } - } finally { - if (!futRec.isDone()) { - // cancel remote Future unless done. - futRec.cancel(true/* mayInterruptIfRunning */); - } - } + } finally { + // cancel the local Future. + futSnd.cancel(true/* mayInterruptIfRunning */); + } + } catch (Throwable t) { + launderPipelineException(true/* isLeader */, member, t); + } + } + + } - } finally { - // cancel the local Future. - futSnd.cancel(true/* mayInterruptIfRunning */); - } + /** + * Launder an exception thrown during pipeline replication. + * @param isLeader + * @param member + * @param t + */ + static private void launderPipelineException(final boolean isLeader, + final QuorumMember<?> member, final Throwable t) { - } catch (Throwable t) { - // check inner cause for downstream PipelineException - final PipelineException pe = (PipelineException) InnerCause - .getInnerCause(t, PipelineException.class); - final UUID problemService; - if (pe != null) { - // throw pe; // throw it upstream - already should have been - // handled - problemService = pe.getProblemServiceId(); - } else { - final UUID[] priorAndNext = member.getQuorum() - .getPipelinePriorAndNext(member.getServiceId()); - problemService = priorAndNext[1]; - } + log.warn("isLeader=" + isLeader + ", t=" + t, t); + + /* + * When non-null, some service downstream of this service had a problem + * replicating to a follower. + */ + final PipelineImmediateDownstreamReplicationException remoteCause = (PipelineImmediateDownstreamReplicationException) InnerCause.getInnerCause(t, + PipelineImmediateDownstreamReplicationException.class); - // determine next pipeline service id - log.warn("Problem with downstream service: " + problemService, - t); + /* + * When non-null, this service has a problem with replication to its + * immediate follower. + * + * Note: if [remoteCause!=null], then we DO NOT look for a direct cause + * (since there will be one wrapped up in the exception trace for some + * remote service rather than for this service). + */ + final ImmediateDownstreamReplicationException directCause = remoteCause == null ? (ImmediateDownstreamReplicationException) InnerCause + .getInnerCause(t, + ImmediateDownstreamReplicationException.class) + : null; - // Carry out remedial work directly - BAD - log.error("Really need to remove service " + problemService); + final UUID thisService = member.getServiceId(); - try { - member.getActor().forceRemoveService(problemService); - } catch (Exception e) { - log.warn("Problem on node removal", e); + final UUID[] priorAndNext = member.getQuorum().getPipelinePriorAndNext( + member.getServiceId()); - throw new RuntimeException(e); - } + if (isLeader) { + + try { + + if (directCause != null) { - throw new PipelineException(problemService, t); + member.getActor().forceRemoveService(priorAndNext[1]); - } - } + } else if (remoteCause != null) { + + final UUID problemService = remoteCause.getProblemServiceId(); + + member.getActor().forceRemoveService(problemService); + + } else { + + // Do not remove anybody. + + } + + } catch (Exception e) { + + log.error("Problem on node removal", e); + + throw new RuntimeException(e); + + } + + } + + if (directCause != null) { + + throw new PipelineImmediateDownstreamReplicationException( + thisService, priorAndNext, t); + + } else if (remoteCause != null) { + + throw new NestedPipelineException(t); + + } else { + + throw new RuntimeException(t); + + } + } /** @@ -1829,10 +1888,11 @@ /* * FIXME We should probably pass the quorum token through from the - * leader for ALL replicated writes. This uses the leader's quorum token - * when it is available (for a live write) and otherwise uses the - * current quorum token (for historical writes, since we are not - * providing the leader's token in this case). + * leader for ALL replicated writes [this is now done by the + * IHASendState but the code is not really using that data yet]. This + * uses the leader's quorum token when it is available (for a live + * write) and otherwise uses the current quorum token (for historical + * writes, since we are not providing the leader's token in this case). */ final long token = req == null ? msg.getQuorumToken() : member .getQuorum().token(); @@ -1966,8 +2026,8 @@ final HAMessageWrapper wrappedMsg = new HAMessageWrapper( req, snd, msg); - // Get Future for send() outcome on local service. - final Future<Void> futSnd = receiveService.receiveData(wrappedMsg, + // Get Future for receive() outcome on local service. + final Future<Void> futRec = receiveService.receiveData(wrappedMsg, b); try { @@ -1978,7 +2038,7 @@ // Verify token remains valid. member.getQuorum().assertQuorum(token); // Await the future. - return futSnd.get(1000, TimeUnit.MILLISECONDS); + return futRec.get(1000, TimeUnit.MILLISECONDS); } catch (TimeoutException ex) { // Timeout. Ignore and retry loop. Thread.sleep(100/* ms */); @@ -1989,7 +2049,7 @@ } finally { // cancel the local Future. - futSnd.cancel(true/*mayInterruptIfRunning*/); + futRec.cancel(true/*mayInterruptIfRunning*/); } @@ -2031,89 +2091,75 @@ } @Override - public Void call() throws Exception { + public Void call() throws Exception { - // wrap the messages together. - final HAMessageWrapper wrappedMsg = new HAMessageWrapper(req, snd, - msg); + // wrap the messages together. + final HAMessageWrapper wrappedMsg = new HAMessageWrapper( + req, snd, msg); - // Get Future for send() outcome on local service. - final Future<Void> futSnd = receiveService.receiveData(wrappedMsg, - b); + // Get Future for receive() outcome on local service. + final Future<Void> futRec = receiveService.receiveData(wrappedMsg, + b); - try { - try { + try { + try { - // Get future for receive outcome on the remote - // service. - final Future<Void> futRec = downstream.service - .receiveAndReplicate(req, snd, msg); + // Get Future for receive outcome on the remote service + // (RMI). + final Future<Void> futRep; + try { + futRep = downstream.service.receiveAndReplicate(req, + snd, msg); + } catch (IOException ex) { // RMI error. + throw new ImmediateDownstreamReplicationException(ex); + } - try { + try { - /* - * Await the Futures, but spend more time waiting on the - * local Future and only check the remote Future every - * second. Timeouts are ignored during this loop. - */ - while (!futSnd.isDone() && !futRec.isDone()) { - /* - * The token must remain valid, even if this service - * is not joined with the met quorum. If fact, - * services MUST replicate writes regardless of - * whether or not they are joined with the met - * quorum, but only while there is a met quorum. - */ - member.getQuorum().assertQuorum(token); - try { - futSnd.get(1L, TimeUnit.SECONDS); - } catch (TimeoutException ignore) { - } - try { - futRec.get(10L, TimeUnit.MILLISECONDS); - } catch (TimeoutException ignore) { - } - } - futSnd.get(); - futRec.get(); + /* + * Await the Futures, but spend more time waiting on the + * local Future and only check the remote Future every + * second. Timeouts are ignored during this loop. + */ + while (!futRec.isDone() && !futRep.isDone()) { + /* + * The token must remain valid, even if this service + * is not joined with the met quorum. If fact, + * services MUST replicate writes regardless of + * whether or not they are joined with the met + * quorum, but only while there is a met quorum. + */ + member.getQuorum().assertQuorum(token); + try { + futRec.get(1L, TimeUnit.SECONDS); + } catch (TimeoutException ignore) { + } + try { + futRep.get(10L, TimeUnit.MILLISECONDS); + } catch (TimeoutException ignore) { + } + } + futRec.get(); + futRep.get(); - } finally { - if (!futRec.isDone()) { - // cancel remote Future unless done. - futRec.cancel(true/* mayInterruptIfRunning */); - } - } + } finally { + if (!futRep.isDone()) { + // cancel remote Future unless done. + futRep.cancel(true/* mayInterruptIfRunning */); + } + } - } finally { - // Is it possible that this cancel conflicts with throwing - // the PipelineException? - // cancel the local Future. - futSnd.cancel(true/* mayInterruptIfRunning */); - } - } catch (Throwable t) { - // determine the problem service, which may be further downstream - // if the Throwable contains a PipelineException innerCause - final PipelineException pe = (PipelineException) InnerCause - .getInnerCause(t, PipelineException.class); - final UUID problemService; - if (pe != null) { - problemService = pe.getProblemServiceId(); - } else { - final UUID[] priorAndNext = member.getQuorum() - .getPipelinePriorAndNext(member.getServiceId()); - problemService = priorAndNext[1]; - } + } finally { + // cancel the local Future. + futRec.cancel(true/* mayInterruptIfRunning */); + } + } catch (Throwable t) { + launderPipelineException(false/* isLeader */, member, t); + } + // done + return null; + } - log.warn("Problem with downstream service: " + problemService, - t); - - throw new PipelineException(problemService, t); - } - - // done - return null; - } - } /** Added: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/AbstractPipelineChangeException.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/AbstractPipelineChangeException.java (rev 0) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/AbstractPipelineChangeException.java 2013-12-13 16:54:30 UTC (rev 7642) @@ -0,0 +1,56 @@ +/** + +Copyright (C) SYSTAP, LLC 2006-2007. All rights reserved. + +Contact: + SYSTAP, LLC + 4501 Tower Road + Greensboro, NC 27410 + lic...@bi... + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; version 2 of the License. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ +/* + * Created on Jun 7, 2013. + */ +package com.bigdata.ha.pipeline; + +/** + * A quorum related exception dealing with the write replication pipeline. + * + * @author <a href="mailto:tho...@us...">Bryan Thompson</a> + */ +abstract public class AbstractPipelineChangeException extends AbstractPipelineException { + + /** + * + */ + private static final long serialVersionUID = 1L; + + public AbstractPipelineChangeException() { + } + + public AbstractPipelineChangeException(String message) { + super(message); + } + + public AbstractPipelineChangeException(Throwable cause) { + super(cause); + } + + public AbstractPipelineChangeException(String message, Throwable cause) { + super(message, cause); + } + +} Added: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/AbstractPipelineException.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/AbstractPipelineException.java (rev 0) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/AbstractPipelineException.java 2013-12-13 16:54:30 UTC (rev 7642) @@ -0,0 +1,55 @@ +/** + +Copyright (C) SYSTAP, LLC 2006-2007. All rights reserved. + +Contact: + SYSTAP, LLC + 4501 Tower Road + Greensboro, NC 27410 + lic...@bi... + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; version 2 of the License. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ +package com.bigdata.ha.pipeline; + +import com.bigdata.quorum.QuorumException; + +/** + * A quorum related exception dealing with the write replication pipeline. + * + * @author <a href="mailto:tho...@us...">Bryan Thompson</a> + */ +abstract public class AbstractPipelineException extends QuorumException { + + /** + * + */ + private static final long serialVersionUID = 1L; + + public AbstractPipelineException() { + } + + public AbstractPipelineException(String message) { + super(message); + } + + public AbstractPipelineException(Throwable cause) { + super(cause); + } + + public AbstractPipelineException(String message, Throwable cause) { + super(message, cause); + } + +} Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HAReceiveService.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HAReceiveService.java 2013-12-13 11:01:37 UTC (rev 7641) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HAReceiveService.java 2013-12-13 16:54:30 UTC (rev 7642) @@ -763,6 +763,10 @@ * more efficient bulk copy operations from the NIO buffer into a local * byte[] on the Java heap against which we then track the evolving * checksum of the data. + * + * FIXME Why isn't this buffer scoped to the outer HAReceiveService? By + * being an inner class field, we allocate it once per payload + * received.... */ private final byte[] a = new byte[512]; @@ -1118,17 +1122,7 @@ callback.incReceive(message, reads, rdlen, rem); } -// if (downstreamFirstCause == null) { -// try { - forwardReceivedBytes(client, rdlen); -// } catch (ExecutionException ex) { -// log.error( -// "Downstream replication failure" -// + ": will drain payload and then rethrow exception: rootCause=" -// + ex, ex); -// downstreamFirstCause = ex; -// } -// } + forwardReceivedBytes(client, rdlen); } // while(itr.hasNext()) @@ -1154,28 +1148,6 @@ + ", actual=" + (int) chk.getValue()); } -// if (downstreamFirstCause != null) { -// -// /** -// * Replication to the downstream service failed. The payload has -// * been fully drained. This ensures that we do not leave part of -// * the payload in the upstream socket channel. We now wrap and -// * rethrow the root cause of the downstream failure. The leader -// * will handle this by forcing the remove of the downstream -// * service and then re-replicating the payload. -// * -// * @see <a -// * href="https://sourceforge.net/apps/trac/bigdata/ticket/724" -// * > HA wire pulling and sure kill testing </a> -// */ -// -// throw new RuntimeException( -// "Downstream replication failure: msg=" + message -// + ", ex=" + downstreamFirstCause, -// downstreamFirstCause); -// -// } - // Check for termination. client.checkFirstCause(); @@ -1211,6 +1183,7 @@ * * @throws ExecutionException * @throws InterruptedException + * @throws ImmediateDownstreamReplicationException * * @todo Since the downstream writes are against a blocking mode * channel, the receiver on this node runs in sync with the @@ -1222,8 +1195,11 @@ * HA wire pulling and sure kill testing </a> */ private void forwardReceivedBytes(final Client client, final int rdlen) - throws InterruptedException, ExecutionException { + throws InterruptedException, ExecutionException, + ImmediateDownstreamReplicationException { + while (true) { + if (rdlen != 0 && addrNextRef.get() != null) { if (log.isTraceEnabled()) log.trace("Incremental send of " + rdlen + " bytes"); @@ -1265,6 +1241,7 @@ : null).get(); } break; // break out of the inner while loop. + } // while(true) } Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HASendService.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HASendService.java 2013-12-13 11:01:37 UTC (rev 7641) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HASendService.java 2013-12-13 16:54:30 UTC (rev 7642) @@ -30,6 +30,7 @@ import java.nio.channels.SocketChannel; import java.nio.channels.WritableByteChannel; import java.util.concurrent.Callable; +import java.util.concurrent.CancellationException; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; import java.util.concurrent.Future; @@ -38,6 +39,9 @@ import org.apache.log4j.Logger; +import com.bigdata.util.InnerCause; +import com.bigdata.util.concurrent.Haltable; + /** * A service for sending raw {@link ByteBuffer}s across a socket. This service * supports the HA write pipeline. This service is designed to be paired with an @@ -82,9 +86,6 @@ private static final Logger log = Logger.getLogger(HASendService.class); -// static final byte ACK = 1; -// static final byte NACK = 0; - /** * The Internet socket address of the receiving service. */ @@ -104,6 +105,7 @@ /* * Note: toString() must be thread-safe. */ + @Override public String toString() { return super.toString() + "{addrNext=" + addrNext + "}"; @@ -295,6 +297,9 @@ * @return The {@link Future} which can be used to await the outcome of this * operation. * + * @throws InterruptedException + * @throws ImmediateDownstreamReplicationException + * * @throws IllegalArgumentException * if the buffer is <code>null</code>. * @throws IllegalArgumentException @@ -305,8 +310,10 @@ * @todo throws IOException if the {@link SocketChannel} was not open and * could not be opened. */ - public Future<Void> send(final ByteBuffer buffer, final byte[] marker) { - + public Future<Void> send(final ByteBuffer buffer, final byte[] marker) + throws ImmediateDownstreamReplicationException, + InterruptedException { + if (buffer == null) throw new IllegalArgumentException(); @@ -324,10 +331,64 @@ // reopenChannel(); - return tmp.submit(newIncSendTask(buffer.asReadOnlyBuffer(), marker)); + try { + return tmp + .submit(newIncSendTask(buffer.asReadOnlyBuffer(), marker)); + + } catch (Throwable t) { + + launderThrowable(t); + + // make the compiler happy. + throw new AssertionError(); + + } + } + /** + * Test the {@link Throwable} for its root cause and distinguish between a + * root cause with immediate downstream replication, normal termination + * through {@link InterruptedException}, {@link CancellationException}, and + * nested {@link AbstractPipelineException}s thrown by a downstream service. + * + * @see <a href="https://sourceforge.net/apps/trac/bigdata/ticket/724" > HA + * wire pulling and sure kill testing </a> + */ + private void launderThrowable(final Throwable t) + throws InterruptedException, + ImmediateDownstreamReplicationException { + + if (Haltable.isTerminationByInterrupt(t)) { + + // root cause is interrupt or cancellation exception. + throw new RuntimeException(t); + + } + + if (InnerCause.isInnerCause(t, AbstractPipelineException.class)) { + + /* + * The root cause is NOT the inability to replicate to our immediate + * downstream service. Instead, some service (not us) has a problem + * with pipline replication. + */ + + throw new NestedPipelineException(t); + + } + + /* + * We have a problem with replication to our immediate downstream + * service. + */ + + throw new ImmediateDownstreamReplicationException(toString(), t); + + } + + /** * A series of timeouts used when we need to re-open the * {@link SocketChannel}. */ Added: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/ImmediateDownstreamReplicationException.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/ImmediateDownstreamReplicationException.java (rev 0) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/ImmediateDownstreamReplicationException.java 2013-12-13 16:54:30 UTC (rev 7642) @@ -0,0 +1,64 @@ +/** + +Copyright (C) SYSTAP, LLC 2006-2013. All rights reserved. + +Contact: + SYSTAP, LLC + 4501 Tower Road + Greensboro, NC 27410 + lic...@bi... + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; version 2 of the License. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ +package com.bigdata.ha.pipeline; + +import java.io.IOException; + + +/** + * An exception thrown by the {@link HAReceiveService} when replication to the + * downstream service fails. The root cause can be an RMI error (can not connect + * or connection lost), a socket channel write error (can not connect, + * connection lost, etc.), or even a transitive error from further down the + * write pipeline. This exception DOES NOT decisively indicate the problem is + * with the immediate downstream service. The caller must inspect the root cause + * to make this determination. However, this exception DOES indicate that the + * problem is with downstream replication rather than with the receipt or + * handling of the payload on this service. + * + * @author <a href="mailto:tho...@us...">Bryan Thompson</a> + */ +public class ImmediateDownstreamReplicationException extends IOException { + + /** + * + */ + private static final long serialVersionUID = 1L; + + public ImmediateDownstreamReplicationException() { + } + + public ImmediateDownstreamReplicationException(String message) { + super(message); + } + + public ImmediateDownstreamReplicationException(Throwable cause) { + super(cause); + } + + public ImmediateDownstreamReplicationException(String message, Throwable cause) { + super(message, cause); + } + +} Added: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/NestedPipelineException.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/NestedPipelineException.java (rev 0) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/NestedPipelineException.java 2013-12-13 16:54:30 UTC (rev 7642) @@ -0,0 +1,55 @@ +/** + +Copyright (C) SYSTAP, LLC 2006-2013. All rights reserved. + +Contact: + SYSTAP, LLC + 4501 Tower Road + Greensboro, NC 27410 + lic...@bi... + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; version 2 of the License. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ +package com.bigdata.ha.pipeline; + +/** + * An exception that is used to wrap and rethrow a cause whose root cause is + * another {@link AbstractPipelineException}. + * + * @author <a href="mailto:tho...@us...">Bryan Thompson</a> + */ +public class NestedPipelineException extends AbstractPipelineException { + + /** + * + */ + private static final long serialVersionUID = 1L; + + public NestedPipelineException() { + super(); + } + + public NestedPipelineException(String message, Throwable cause) { + super(message, cause); + } + + public NestedPipelineException(String message) { + super(message); + } + + public NestedPipelineException(Throwable cause) { + super(cause); + } + +} Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/PipelineDownstreamChange.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/PipelineDownstreamChange.java 2013-12-13 11:01:37 UTC (rev 7641) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/PipelineDownstreamChange.java 2013-12-13 16:54:30 UTC (rev 7642) @@ -42,7 +42,7 @@ * * @author <a href="mailto:tho...@us...">Bryan Thompson</a> */ -public class PipelineDownstreamChange extends QuorumException { +public class PipelineDownstreamChange extends AbstractPipelineChangeException { /** * Copied: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/PipelineImmediateDownstreamReplicationException.java (from rev 7640, branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/PipelineException.java) =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/PipelineImmediateDownstreamReplicationException.java (rev 0) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/PipelineImmediateDownstreamReplicationException.java 2013-12-13 16:54:30 UTC (rev 7642) @@ -0,0 +1,113 @@ +/** + +Copyright (C) SYSTAP, LLC 2006-2013. All rights reserved. + +Contact: + SYSTAP, LLC + 4501 Tower Road + Greensboro, NC 27410 + lic...@bi... + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; version 2 of the License. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ + +package com.bigdata.ha.pipeline; + +import java.util.UUID; + +/** + * Exception thrown when there is a problem with write replication from a + * service to its downstream service, including a problem with RMI to the + * downstream service or socket level write replication to the downstream + * service. This typed exception enables the leader is then able to take action + * intended to cure the pipeline by forcing the problem service from the quorum. + * The problem service can then attempt to re-enter the quorum. + */ +public class PipelineImmediateDownstreamReplicationException extends + AbstractPipelineException { + + /** + * Generated ID + */ + private static final long serialVersionUID = 8019938954269914574L; + + /** + * The {@link UUID} of the service reporting a problem replicating writes to + * its downstream service. + */ + private final UUID serviceId; + + /** + * The prior and next service {@link UUID}s for the service reporting the + * problem. The problem is with the communication to the "next" service. + */ + private final UUID[] priorAndNext; + + /** + * + * @param serviceId + * The {@link UUID} of the service reporting a problem + * replicating writes to its downstream service. + * @param priorAndNext + * The prior and next service {@link UUID}s for the service + * reporting the problem. The problem is with the communication + * to the "next" service. + * @param t + * The root cause exception. + */ + public PipelineImmediateDownstreamReplicationException(final UUID serviceId, + final UUID[] priorAndNext, final Throwable t) { + + super(t); + + this.serviceId = serviceId; + + this.priorAndNext = priorAndNext; + + } + + /** + * Return the {@link UUID} of the service reporting the problem. This is the + * service that attempted to replicate a payload to the downstream service + * and was unable to replicate the payload due to the reported root cause. + */ + public UUID getReportingServiceId() { + + return serviceId; + + } + + /** + * The prior and next service {@link UUID}s for the service reporting the + * problem. The problem is with the communication to the "next" service. + */ + public UUID[] getPriorAndNext() { + + return priorAndNext; + + } + + /** + * Return the {@link UUID} of the downstream service - the problem is + * reported for the communication channel between the reporting service and + * this downstream service. The downstream service is the service that + * should be forced out of the quorum in order to "fix" the pipeline. + */ + public UUID getProblemServiceId() { + + return priorAndNext[1]; + + } + +} Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/PipelineUpstreamChange.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/PipelineUpstreamChange.java 2013-12-13 11:01:37 UTC (rev 7641) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/PipelineUpstreamChange.java 2013-12-13 16:54:30 UTC (rev 7642) @@ -29,7 +29,6 @@ import java.util.concurrent.CancellationException; import com.bigdata.ha.QuorumPipelineImpl; -import com.bigdata.quorum.QuorumException; /** * Exception thrown when the upstream service is changed by a pipeline @@ -42,7 +41,7 @@ * * @author <a href="mailto:tho...@us...">Bryan Thompson</a> */ -public class PipelineUpstreamChange extends QuorumException { +public class PipelineUpstreamChange extends AbstractPipelineChangeException { /** * Modified: branches/MGC_1_3_0/bigdata/src/test/com/bigdata/ha/pipeline/TestHASendAndReceive.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/test/com/bigdata/ha/pipeline/TestHASendAndReceive.java 2013-12-13 11:01:37 UTC (rev 7641) +++ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/ha/pipeline/TestHASendAndReceive.java 2013-12-13 16:54:30 UTC (rev 7642) @@ -114,8 +114,9 @@ * @throws ExecutionException * @throws InterruptedException * @throws TimeoutException + * @throws ImmediateDownstreamReplicationException */ - public void testSimpleExchange() throws InterruptedException, ExecutionException, TimeoutException { + public void testSimpleExchange() throws InterruptedException, ExecutionException, TimeoutException, ImmediateDownstreamReplicationException { final long timeout = 5000;// ms { @@ -149,9 +150,10 @@ * @throws TimeoutException * @throws ExecutionException * @throws InterruptedException + * @throws ImmediateDownstreamReplicationException */ public void testStress() throws TimeoutException, InterruptedException, - ExecutionException { + ExecutionException, ImmediateDownstreamReplicationException { final long timeout = 5000; // ms for (int i = 0; i < 100; i++) { Modified: branches/MGC_1_3_0/bigdata/src/test/com/bigdata/ha/pipeline/TestHASendAndReceive3Nodes.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/test/com/bigdata/ha/pipeline/TestHASendAndReceive3Nodes.java 2013-12-13 11:01:37 UTC (rev 7641) +++ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/ha/pipeline/TestHASendAndReceive3Nodes.java 2013-12-13 16:54:30 UTC (rev 7642) @@ -159,7 +159,7 @@ } public void testSimpleExchange() throws InterruptedException, - ExecutionException, TimeoutException { + ExecutionException, TimeoutException, ImmediateDownstreamReplicationException { final long timeout = 5000; // ms final ByteBuffer tst1 = getRandomData(50); @@ -177,7 +177,7 @@ assertEquals(rcv1, rcv2); } - public void testChecksumError() throws InterruptedException, ExecutionException + public void testChecksumError() throws InterruptedException, ExecutionException, ImmediateDownstreamReplicationException { final ByteBuffer tst1 = getRandomData(50); Modified: branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHA3JustKills.java =================================================================== --- branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHA3JustKills.java 2013-12-13 11:01:37 UTC (rev 7641) +++ branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHA3JustKills.java 2013-12-13 16:54:30 UTC (rev 7642) @@ -87,6 +87,10 @@ final long token = awaitFullyMetQuorum(); + // await the initial KB commit on all services. + awaitCommitCounter(1L, new HAGlue[] { startup.serverA, startup.serverB, + startup.serverC }); + // start concurrent task loads that continue until fully met final FutureTask<Void> ft = new FutureTask<Void>(new LargeLoadTask( token)); @@ -94,7 +98,7 @@ executorService.submit(ft); // allow load head start - Thread.sleep(300/* ms */); + Thread.sleep(2000/* ms */); // Verify load is still running. assertFalse(ft.isDone()); @@ -103,11 +107,10 @@ log.warn("ZOOKEEPER\n" + dumpZoo()); kill(startup.serverC); - - // FIXME: in the face of no implemented error propagation we can explicitly - // tell the leader to remove the killed service! - // startup.serverA.submit(new ForceRemoveService(getServiceCId()), true).get(); + // Note: Automatic. +// startup.serverA.submit(new ForceRemoveService(getServiceCId()), true).get(); + awaitPipeline(20, TimeUnit.SECONDS, new HAGlue[] {startup.serverA, startup.serverB}); // token must remain unchanged to indicate same quorum @@ -153,6 +156,10 @@ final long token = awaitFullyMetQuorum(); + // await the initial KB commit on all services. + awaitCommitCounter(1L, new HAGlue[] { startup.serverA, startup.serverB, + startup.serverC }); + // start concurrent task loads that continue until fully met final FutureTask<Void> ft = new FutureTask<Void>(new LargeLoadTask( token)); @@ -160,7 +167,7 @@ executorService.submit(ft); // allow load head start - Thread.sleep(1000/* ms */); + Thread.sleep(2000/* ms */); // Verify load is still running. assertFalse(ft.isDone()); @@ -170,8 +177,8 @@ kill(startup.serverB); - // FIXME: temporary call to explicitly remove the service prior to correct protocol - // startup.serverA.submit(new ForceRemoveService(getServiceBId()), true).get(); + // Note: automatic. +// startup.serverA.submit(new ForceRemoveService(getServiceBId()), true).get(); awaitPipeline(10, TimeUnit.SECONDS, new HAGlue[] {startup.serverA, startup.serverC}); @@ -311,15 +318,10 @@ // Dump Zookeeper log.warn("ZOOKEEPER\n" + dumpZoo()); - // Note: sure kill is done automatically when we hit the desired point - // in the write replication. - // kill(startup.serverB); + // Note: automatic. +// startup.serverA.submit(new ForceRemoveService(getServiceBId()), true) +// .get(); - // FIXME: temporary call to explicitly remove the service prior to - // correct protocol - // startup.serverA.submit(new ForceRemoveService(getServiceBId()), true) - // .get(); - awaitPipeline(10, TimeUnit.SECONDS, new HAGlue[] { startup.serverA, startup.serverC }); @@ -390,15 +392,10 @@ // Dump Zookeeper log.warn("ZOOKEEPER\n" + dumpZoo()); - // Note: sure kill is done automatically when we hit the desired point - // in the write replication. - // kill(startup.serverB); + // Note: automatic. +// startup.serverA.submit(new ForceRemoveService(getServiceCId()), true) +// .get(); - // FIXME: temporary call to explicitly remove the service prior to - // correct protocol - // startup.serverA.submit(new ForceRemoveService(getServiceCId()), true) - // .get(); - awaitPipeline(10, TimeUnit.SECONDS, new HAGlue[] { startup.serverA, startup.serverB }); @@ -415,11 +412,83 @@ // token must remain unchanged to indicate same quorum assertEquals(token, awaitMetQuorum()); - // TODO We could finally restart the killed service and verify resync. - } /** + * Start A+B+C in strict sequence. Wait until the quorum fully meets. Start + * a long running LOAD. While the LOAD is running, C will issue a sure kill + * of B (the 1st follower) when it has received a specified number of bytes + * of data from B. Verify that the LOAD completes successfully with the + * remaining services (A+C). + */ + public void testABC_LiveLoadRemainsMet_C_kills_B_duringIncrementalReplication() + throws Exception { + + // enforce join order + final ABC startup = new ABC(true /* sequential */); + + final long token = awaitFullyMetQuorum(); + + // await the initial KB commit on all services. + awaitCommitCounter(1L, new HAGlue[] { startup.serverA, startup.serverB, + startup.serverC }); + + // Set a trigger to sure kill B once C reaches the specified + // replication point. + ((HAGlueTest) startup.serverC) + .failWriteReplication(new HAProgressListenerKillPID_1( + ((HAGlueTest) startup.serverB).getPID())); + + // start large load. + final FutureTask<Void> ft = new FutureTask<Void>(new LargeLoadTask( + token)); + + executorService.submit(ft); + + // Wait until B is killed. + assertCondition(new Runnable() { + public void run() { + try { + startup.serverB.getWritePipelineAddr(); + fail("B is still running."); + } catch (IOException ex) { + if (log.isInfoEnabled()) + log.info("Expected exception: B is no longer responding: " + + ex); + return; + } + } + }, 20000, TimeUnit.MILLISECONDS); + + // Verify load is still running. + assertFalse(ft.isDone()); + + // Dump Zookeeper + log.warn("ZOOKEEPER\n" + dumpZoo()); + + // Note: automatic. +// startup.serverA.submit(new ForceRemoveService(getServiceCId()), true) +// .get(); + + awaitPipeline(10, TimeUnit.SECONDS, new HAGlue[] { startup.serverA, + startup.serverC }); + + // also check members and joined + awaitMembers(new HAGlue[] { startup.serverA, startup.serverC }); + awaitJoined(new HAGlue[] { startup.serverA, startup.serverC }); + + // token must remain unchanged to indicate same quorum + assertEquals(token, awaitMetQuorum()); + + // Await LOAD, but with a timeout. + ft.get(longLoadTimeoutMillis, TimeUnit.MILLISECONDS); + + // token must remain unchanged to indicate same quorum + assertEquals(token, awaitMetQuorum()); + + } + + /** * Test where we start A+B+C in strict sequence. Once we observe that all * services have gone through the initial KB create, we do a sudden kill of * B. We then start the live load. This test explores what happens when A is @@ -471,8 +540,6 @@ * C. We then start the live load. This test explores what happens when A * and B are not yet aware that C is dead when the UPDATE operation starts. * - * Can I commit this - * * @throws Exception */ public void testABC_awaitKBCreate_killC_LiveLoadRemainsMet() @@ -495,9 +562,9 @@ executorService.submit(ft); - // FIXME RESYNC_PIPELINE: move into QuorumPipelineImpl. - // startup.serverA.submit(new ForceRemoveService(getServiceCId()), true) - // .get(); + // Note: Automatic. +// startup.serverA.submit(new ForceRemoveService(getServiceCId()), true) +// .get(); awaitPipeline(getZKSessionTimeout() + 5000, TimeUnit.MILLISECONDS, new HAGlue[] { startup.serverA, startup.serverB }); This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |
From: <tho...@us...> - 2013-12-17 17:28:04
|
Revision: 7667 http://bigdata.svn.sourceforge.net/bigdata/?rev=7667&view=rev Author: thompsonbry Date: 2013-12-17 17:27:53 +0000 (Tue, 17 Dec 2013) Log Message: ----------- Added a resetPipeline() method to HAPipelineGlue. This is intended to reset each service that is in the pipeline when the leader launders a pipeline exception. See #724 Modified Paths: -------------- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/HAPipelineGlue.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumCommitImpl.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipeline.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumServiceBase.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HAReceiveService.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HASendService.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/journal/AbstractJournal.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/QuorumClient.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/io/writecache/TestWORMWriteCacheService.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/quorum/MockQuorumFixture.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/HAJournalTest.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHAJournalServer.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/quorum/zk/MockQuorumMember.java Added Paths: ----------- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/AbstractMessageTask.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/HAPipelineResetRequest.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/HAPipelineResetResponse.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/IHAPipelineResetRequest.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/IHAPipelineResetResponse.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/ServiceLookup.java Added: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/AbstractMessageTask.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/AbstractMessageTask.java (rev 0) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/AbstractMessageTask.java 2013-12-17 17:27:53 UTC (rev 7667) @@ -0,0 +1,87 @@ +package com.bigdata.ha; + +import java.io.IOException; +import java.rmi.Remote; +import java.util.UUID; +import java.util.concurrent.Callable; +import java.util.concurrent.Future; + +import com.bigdata.ha.msg.IHAMessage; +import com.bigdata.quorum.ServiceLookup; + +/** + * Helper class submits the RMI for a PREPARE, COMMIT, or ABORT message. This is + * used to execute the different requests in parallel on a local executor + * service. + * + * @author <a href="mailto:tho...@us...">Bryan Thompson</a> + */ +abstract class AbstractMessageTask<S extends Remote, T, M extends IHAMessage> + implements Callable<T> { + + private final ServiceLookup<S> serviceLookup; + private final UUID serviceId; + protected final M msg; + + public AbstractMessageTask(final ServiceLookup<S> serviceLookup, + final UUID serviceId, final M msg) { + + this.serviceLookup = serviceLookup; + + this.serviceId = serviceId; + + this.msg = msg; + + } + + @Override + final public T call() throws Exception { + + /* + * Note: This code MAY be interrupted at any point if the Future for the + * task is cancelled. If it is interrupted during the RMI, then the + * expectation is that the NIO will be interrupted in a timely manner + * throwing back some sort of IOException indicating the asynchronous + * close of the IO channel or cancel of the RMI. + */ + + // Resolve proxy for remote service. + final S service = serviceLookup.getService(serviceId); + + // RMI. + final Future<T> ft = doRMI(service); + + try { + + /* + * Await the inner Future for the RMI. + * + * Note: In fact, this is a ThickFuture so it is already done by the + * time the RMI returns. + */ + + return ft.get(); + + } finally { + + ft.cancel(true/* mayInterruptIfRunning */); + + } + + } + + /** + * Invoke the specific RMI using the message supplied to the constructor. + * + * @param service + * The service (resolved from the service {@link UUID} supplied + * to the constructor). + * + * @return The result of submitting that RMI to the remote service. + * + * @throws IOException + * if there is a problem with the RMI. + */ + abstract protected Future<T> doRMI(final S service) throws IOException; + +} \ No newline at end of file Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/HAPipelineGlue.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/HAPipelineGlue.java 2013-12-17 01:00:14 UTC (rev 7666) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/HAPipelineGlue.java 2013-12-17 17:27:53 UTC (rev 7667) @@ -43,6 +43,8 @@ import com.bigdata.ha.msg.IHAWriteMessage; import com.bigdata.ha.msg.IHAWriteSetStateRequest; import com.bigdata.ha.msg.IHAWriteSetStateResponse; +import com.bigdata.ha.pipeline.HAReceiveService; +import com.bigdata.ha.pipeline.HASendService; import com.bigdata.io.writecache.WriteCache; import com.bigdata.journal.WriteExecutorService; import com.bigdata.service.proxy.ThickFuture; @@ -121,6 +123,26 @@ Future<Void> moveToEndOfPipeline() throws IOException; /** + * Reset the pipeline (blocking). This message is used to handle an error in + * pipeline replication. If replication fails, the socket connections both + * upstream and downstream of the point of failure can be left in an + * indeterminate state with partially buffered data. In order to bring the + * pipeline back into a known state (without forcing a quorum break) we + * message each service in the pipeline to reset its + * {@link HAReceiveService} (including the inner {@link HASendService}). The + * next message and payload relayed from the leader will cause new socket + * connections to be established. + * + * @param msg The request. + * + * @return The {@link Future} for the operation on the remote service. + * + * @throws IOException + */ + Future<IHAPipelineResetResponse> resetPipeline(IHAPipelineResetRequest req) + throws IOException; + + /** * Accept metadata describing an NIO buffer transfer along the write * pipeline. This method is never invoked on the master. It is only invoked * on the failover nodes, including the last node in the failover chain. Added: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/HAPipelineResetRequest.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/HAPipelineResetRequest.java (rev 0) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/HAPipelineResetRequest.java 2013-12-17 17:27:53 UTC (rev 7667) @@ -0,0 +1,49 @@ +/** + +Copyright (C) SYSTAP, LLC 2006-2010. All rights reserved. + +Contact: + SYSTAP, LLC + 4501 Tower Road + Greensboro, NC 27410 + lic...@bi... + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; version 2 of the License. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ +package com.bigdata.ha; + +public class HAPipelineResetRequest implements IHAPipelineResetRequest { + + /** + * + */ + private static final long serialVersionUID = 1L; + + private long token; + + public HAPipelineResetRequest(final long token) { + this.token = token; + } + + @Override + public long token() { + return token; + } + + @Override + public String toString() { + return super.toString() + "{token=" + token + "}"; + } + +} Added: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/HAPipelineResetResponse.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/HAPipelineResetResponse.java (rev 0) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/HAPipelineResetResponse.java 2013-12-17 17:27:53 UTC (rev 7667) @@ -0,0 +1,33 @@ +/** + +Copyright (C) SYSTAP, LLC 2006-2010. All rights reserved. + +Contact: + SYSTAP, LLC + 4501 Tower Road + Greensboro, NC 27410 + lic...@bi... + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; version 2 of the License. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ +package com.bigdata.ha; + +public class HAPipelineResetResponse implements IHAPipelineResetResponse { + + /** + * + */ + private static final long serialVersionUID = 1L; + +} Added: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/IHAPipelineResetRequest.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/IHAPipelineResetRequest.java (rev 0) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/IHAPipelineResetRequest.java 2013-12-17 17:27:53 UTC (rev 7667) @@ -0,0 +1,40 @@ +/** + +Copyright (C) SYSTAP, LLC 2006-2010. All rights reserved. + +Contact: + SYSTAP, LLC + 4501 Tower Road + Greensboro, NC 27410 + lic...@bi... + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; version 2 of the License. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ +package com.bigdata.ha; + +import com.bigdata.ha.msg.IHAMessage; + +/** + * Message requesting a pipeline reset on a service. + * + * @author <a href="mailto:tho...@us...">Bryan Thompson</a> + */ +public interface IHAPipelineResetRequest extends IHAMessage { + + /** + * The quorum token in effect on the leader when this request was generated. + */ + long token(); + +} Added: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/IHAPipelineResetResponse.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/IHAPipelineResetResponse.java (rev 0) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/IHAPipelineResetResponse.java 2013-12-17 17:27:53 UTC (rev 7667) @@ -0,0 +1,35 @@ +/** + +Copyright (C) SYSTAP, LLC 2006-2010. All rights reserved. + +Contact: + SYSTAP, LLC + 4501 Tower Road + Greensboro, NC 27410 + lic...@bi... + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; version 2 of the License. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ +package com.bigdata.ha; + +import com.bigdata.ha.msg.IHAMessage; + +/** + * Message reporting the outcome of a pipeline reset on a service. + * + * @author <a href="mailto:tho...@us...">Bryan Thompson</a> + */ +public interface IHAPipelineResetResponse extends IHAMessage { + +} Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumCommitImpl.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumCommitImpl.java 2013-12-17 01:00:14 UTC (rev 7666) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumCommitImpl.java 2013-12-17 17:27:53 UTC (rev 7667) @@ -28,7 +28,6 @@ import java.util.LinkedList; import java.util.List; import java.util.UUID; -import java.util.concurrent.Callable; import java.util.concurrent.CancellationException; import java.util.concurrent.ExecutionException; import java.util.concurrent.ExecutorService; @@ -44,14 +43,12 @@ import com.bigdata.ha.msg.IHA2PhaseAbortMessage; import com.bigdata.ha.msg.IHA2PhaseCommitMessage; import com.bigdata.ha.msg.IHA2PhasePrepareMessage; -import com.bigdata.ha.msg.IHAMessage; import com.bigdata.journal.IRootBlockView; import com.bigdata.quorum.Quorum; import com.bigdata.quorum.QuorumMember; import com.bigdata.quorum.QuorumStateChangeListener; import com.bigdata.quorum.QuorumStateChangeListenerBase; -import com.bigdata.service.proxy.ThickFuture; -import com.bigdata.util.InnerCause; +import com.bigdata.quorum.ServiceLookup; import com.bigdata.util.concurrent.ExecutionExceptions; /** @@ -59,9 +56,9 @@ */ public class QuorumCommitImpl<S extends HACommitGlue> extends QuorumStateChangeListenerBase implements QuorumCommit<S>, - QuorumStateChangeListener { + QuorumStateChangeListener, ServiceLookup<HACommitGlue> { - static private transient final Logger log = Logger + static transient final Logger log = Logger .getLogger(QuorumCommitImpl.class); private final QuorumMember<S> member; @@ -83,62 +80,13 @@ return member.getQuorum(); } - - private HACommitGlue getService(final UUID serviceId) { + public HACommitGlue getService(final UUID serviceId) { + return member.getService(serviceId); } - - /** - * Cancel the requests on the remote services (RMI). This is a best effort - * implementation. Any RMI related errors are trapped and ignored in order - * to be robust to failures in RMI when we try to cancel the futures. - * <p> - * NOte: This is not being done in parallel. However, due to a DGC thread - * leak issue, we now use {@link ThickFuture}s. Thus, the tasks that are - * being cancelled are all local tasks running on the - * {@link #executorService}. If that local task is doing an RMI, then - * cancelling it will cause an interrupt in the NIO request. - */ - private <F extends Future<T>, T> void cancelFutures(final List<F> futures) { - if (log.isInfoEnabled()) - log.info(""); - - for (F f : futures) { - - if (f == null) { - - continue; - - } - - try { - - if (!f.isDone()) { - - f.cancel(true/* mayInterruptIfRunning */); - - } - - } catch (Throwable t) { - - if (InnerCause.isInnerCause(t, InterruptedException.class)) { - - // Propagate interrupt. - Thread.currentThread().interrupt(); - - } - - // ignored (to be robust). - - } - - } - - } - /** * {@inheritDoc} * <p> @@ -270,7 +218,7 @@ * remote service. We will await this task below. */ final Future<Boolean> rf = executorService - .submit(new PrepareMessageTask(serviceId, + .submit(new PrepareMessageTask(this, serviceId, msgForJoinedService)); // add to list of futures we will check. @@ -379,7 +327,7 @@ } finally { - cancelFutures(localFutures); + QuorumServiceBase.cancelFutures(localFutures); } @@ -469,7 +417,7 @@ * remote service. */ final Future<Void> rf = executorService - .submit(new CommitMessageTask(serviceId, + .submit(new CommitMessageTask(this, serviceId, msgJoinedService)); // add to list of futures we will check. @@ -533,7 +481,7 @@ } finally { // Ensure that all futures are cancelled. - cancelFutures(localFutures); + QuorumServiceBase.cancelFutures(localFutures); } @@ -580,7 +528,7 @@ * remote service. */ final Future<Void> rf = executorService - .submit(new AbortMessageTask(serviceId, msg)); + .submit(new AbortMessageTask(this, serviceId, msg)); // add to list of futures we will check. localFutures.add(rf); @@ -643,86 +591,24 @@ } finally { // Ensure that all futures are cancelled. - cancelFutures(localFutures); + QuorumServiceBase.cancelFutures(localFutures); } } - /** - * Helper class submits the RMI for a PREPARE, COMMIT, or ABORT message. - * This is used to execute the different requests in parallel on a local - * executor service. - * - * @author <a href="mailto:tho...@us...">Bryan - * Thompson</a> - */ - private abstract class AbstractMessageTask<T, M extends IHAMessage> - implements Callable<T> { + static private class PrepareMessageTask extends + AbstractMessageTask<HACommitGlue, Boolean, IHA2PhasePrepareMessage> { - private final UUID serviceId; - protected final M msg; + public PrepareMessageTask( + final ServiceLookup<HACommitGlue> serviceLookup, + final UUID serviceId, final IHA2PhasePrepareMessage msg) { - public AbstractMessageTask(final UUID serviceId, final M msg) { + super(serviceLookup, serviceId, msg); - this.serviceId = serviceId; - - this.msg = msg; - } @Override - final public T call() throws Exception { - - /* - * Note: This code MAY be interrupted at any point if the Future for - * the task is cancelled. If it is interrupted during the RMI, then - * the expectation is that the NIO will be interrupted in a timely - * manner throwing back some sort of IOException indicating the - * asynchronous close of the IO channel or cancel of the RMI. - */ - - // Resolve proxy for remote service. - final HACommitGlue service = getService(serviceId); - - // RMI. - final Future<T> ft = doRMI(service); - - try { - - /* - * Await the inner Future for the RMI. - * - * Note: In fact, this is a ThickFuture so it is already done by - * the time the RMI returns. - */ - - return ft.get(); - - } finally { - - ft.cancel(true/* mayInterruptIfRunning */); - - } - - } - - abstract protected Future<T> doRMI(final HACommitGlue service) - throws IOException; - - } - - private class PrepareMessageTask extends - AbstractMessageTask<Boolean, IHA2PhasePrepareMessage> { - - public PrepareMessageTask(final UUID serviceId, - final IHA2PhasePrepareMessage msg) { - - super(serviceId, msg); - - } - - @Override protected Future<Boolean> doRMI(final HACommitGlue service) throws IOException { @@ -732,13 +618,14 @@ } - private class CommitMessageTask extends - AbstractMessageTask<Void, IHA2PhaseCommitMessage> { + static private class CommitMessageTask extends + AbstractMessageTask<HACommitGlue, Void, IHA2PhaseCommitMessage> { - public CommitMessageTask(final UUID serviceId, - final IHA2PhaseCommitMessage msg) { + public CommitMessageTask( + final ServiceLookup<HACommitGlue> serviceLookup, + final UUID serviceId, final IHA2PhaseCommitMessage msg) { - super(serviceId, msg); + super(serviceLookup, serviceId, msg); } @@ -751,13 +638,14 @@ } - private class AbortMessageTask extends - AbstractMessageTask<Void, IHA2PhaseAbortMessage> { + static private class AbortMessageTask extends + AbstractMessageTask<HACommitGlue, Void, IHA2PhaseAbortMessage> { - public AbortMessageTask(final UUID serviceId, - final IHA2PhaseAbortMessage msg) { + public AbortMessageTask( + final ServiceLookup<HACommitGlue> serviceLookup, + final UUID serviceId, final IHA2PhaseAbortMessage msg) { - super(serviceId, msg); + super(serviceLookup, serviceId, msg); } @@ -769,5 +657,5 @@ } } - + } Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipeline.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipeline.java 2013-12-17 01:00:14 UTC (rev 7666) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipeline.java 2013-12-17 17:27:53 UTC (rev 7667) @@ -36,6 +36,8 @@ import com.bigdata.ha.msg.IHASendState; import com.bigdata.ha.msg.IHASyncRequest; import com.bigdata.ha.msg.IHAWriteMessage; +import com.bigdata.ha.pipeline.HAReceiveService; +import com.bigdata.ha.pipeline.HASendService; import com.bigdata.io.writecache.WriteCache; import com.bigdata.journal.IRootBlockView; import com.bigdata.quorum.Quorum; @@ -95,6 +97,26 @@ Future<Void> receiveAndReplicate(IHASyncRequest req, IHASendState snd, IHAWriteMessage msg) throws IOException; + /** + * Reset the pipeline (blocking). This message is used to handle an error in + * pipeline replication. If replication fails, the socket connections both + * upstream and downstream of the point of failure can be left in an + * indeterminate state with partially buffered data. In order to bring the + * pipeline back into a known state (without forcing a quorum break) we + * message each service in the pipeline to reset its + * {@link HAReceiveService} (including the inner {@link HASendService}). The + * next message and payload relayed from the leader will cause new socket + * connections to be established. + * + * @param msg The request. + * + * @return The {@link Future} for the operation on the local service. + * + * @throws IOException + */ + Future<IHAPipelineResetResponse> resetPipeline(IHAPipelineResetRequest req) + throws IOException; + /* * Note: Method removed since it does not appear necessary to let this * service out of the scope of the QuorumPipelineImpl and the send service Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java 2013-12-17 01:00:14 UTC (rev 7666) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java 2013-12-17 17:27:53 UTC (rev 7667) @@ -30,6 +30,8 @@ import java.net.InetSocketAddress; import java.nio.ByteBuffer; import java.util.Iterator; +import java.util.LinkedList; +import java.util.List; import java.util.UUID; import java.util.concurrent.BlockingQueue; import java.util.concurrent.Callable; @@ -70,7 +72,9 @@ import com.bigdata.quorum.QuorumStateChangeEventEnum; import com.bigdata.quorum.QuorumStateChangeListener; import com.bigdata.quorum.QuorumStateChangeListenerBase; +import com.bigdata.quorum.ServiceLookup; import com.bigdata.util.InnerCause; +import com.bigdata.util.concurrent.ExecutionExceptions; /** * {@link QuorumPipeline} implementation. @@ -1197,6 +1201,61 @@ } + @Override + public Future<IHAPipelineResetResponse> resetPipeline( + final IHAPipelineResetRequest req) throws IOException { + + final FutureTask<IHAPipelineResetResponse> ft = new FutureTask<IHAPipelineResetResponse>( + new ResetPipelineTaskImpl(req)); + + member.getExecutor().submit(ft); + + return ft; + + } + + /** + * Task resets the pipeline on this service. + * + * @author <a href="mailto:tho...@us...">Bryan Thompson</a> + */ + private class ResetPipelineTaskImpl implements + Callable<IHAPipelineResetResponse> { + + @SuppressWarnings("unused") + private final IHAPipelineResetRequest req; + + public ResetPipelineTaskImpl(final IHAPipelineResetRequest req) { + + this.req = req; + + } + + @Override + public IHAPipelineResetResponse call() throws Exception { + + // FIXME Versus using the inner handler? +// innerEventHandler.pipelineUpstreamChange(); +// innerEventHandler.pipelineChange(oldDownStreamId, newDownStreamId); + + if (receiveService != null) { + + receiveService.changeUpStream(); + + } + + if (sendService != null) { + + sendService.closeChannel(); + + } + + return new HAPipelineResetResponse(); + + } + + } + /* * This is the leader, so send() the buffer. */ @@ -1558,7 +1617,8 @@ final ByteBuffer b = this.b.duplicate(); new SendBufferTask<S>(member, quorumToken, req, snd, msg, b, - downstream, sendService, sendLock).call(); + downstream, sendService, QuorumPipelineImpl.this, + sendLock).call(); return; @@ -1687,13 +1747,15 @@ private final ByteBuffer b; private final PipelineState<S> downstream; private final HASendService sendService; + private final QuorumPipelineImpl<S> outerClass; private final Lock sendLock; public SendBufferTask(final QuorumMember<S> member, final long token, final IHASyncRequest req, final IHASendState snd, final IHAWriteMessage msg, final ByteBuffer b, final PipelineState<S> downstream, - final HASendService sendService, final Lock sendLock) { + final HASendService sendService, + final QuorumPipelineImpl outerClass, final Lock sendLock) { this.member = member; this.token = token; @@ -1703,6 +1765,7 @@ this.b = b; this.downstream = downstream; this.sendService = sendService; + this.outerClass = outerClass; this.sendLock = sendLock; } @@ -1785,27 +1848,33 @@ } finally { // cancel the local Future. - futSnd.cancel(true/* mayInterruptIfRunning */); // FIXME Cancel hits wrong send() payload. + futSnd.cancel(true/* mayInterruptIfRunning */); } } catch (Throwable t) { - launderPipelineException(true/* isLeader */, member, t); + launderPipelineException(true/* isLeader */, token, member, outerClass, t); } } - } + } // class SendBufferTask /** * Launder an exception thrown during pipeline replication. * * @param isLeader * <code>true</code> iff this service is the quorum leader. + * @param token + * The quorum token. * @param member * The {@link QuorumMember} for this service. + * @param outerClass + * The outer class - required for {@link #resetPipeline()}. * @param t * The throwable. */ - static private void launderPipelineException(final boolean isLeader, - final QuorumMember<?> member, final Throwable t) { + static private <S extends HAPipelineGlue> void launderPipelineException( + final boolean isLeader, final long token, + final QuorumMember<S> member, final QuorumPipelineImpl outerClass, + final Throwable t) { log.warn("isLeader=" + isLeader + ", t=" + t, t); @@ -1838,6 +1907,11 @@ try { + /* + * If we can identify the problem service, then force it out of + * the pipeline. It can re-enter the pipeline once it + * transitions through its ERROR state. + */ if (directCause != null) { member.getActor().forceRemoveService(priorAndNext[1]); @@ -1854,6 +1928,23 @@ } + /** + * Reset the pipeline on each service (including the leader). If + * replication fails, the socket connections both upstream and + * downstream of the point of failure can be left in an + * indeterminate state with partially buffered data. In order to + * bring the pipeline back into a known state (without forcing a + * quorum break) we message each service in the pipeline to + * reset its HAReceiveService (including the inner + * HASendService. The next message and payload relayed from the + * leader will cause new socket connections to be established. + * + * @see <a + * href="https://sourceforge.net/apps/trac/bigdata/ticket/724" + * > HA Wire Pulling and Sudden Kills </a> + */ + outerClass.resetPipeline(token); + } catch (Exception e) { log.error("Problem on node removal", e); @@ -1880,8 +1971,145 @@ } } - + /** + * Issue concurrent requests to each service in the pipeline to reset the + * pipeline on that service. The request to the leader is executed in the + * caller's thread so it will own whatever locks the caller already owns - + * this is done to avoid deadlock. + * + * @param token + * The quorum token on the leader. + * @param member + */ + private void resetPipeline(final long token) { + + log.error("Leader will reset pipeline: " + token); + + /* + * We will only message the services that are in the pipeline. + * + * For services (other than the leader) in the quorum, submit the + * RunnableFutures to an Executor. + * + * For the leader, we do this in the caller's thread (to avoid + * possible deadlocks). + */ + final UUID[] pipelineIds = member.getQuorum().getPipeline(); + + member.assertLeader(token); + + final IHAPipelineResetRequest msg = new HAPipelineResetRequest(token); + + /* + * To minimize latency, we first submit the futures for the other + * services and then do f.run() on the leader. + */ + final List<Future<IHAPipelineResetResponse>> localFutures = new LinkedList<Future<IHAPipelineResetResponse>>(); + + try { + + for (int i = 1; i < pipelineIds.length; i++) { + + final UUID serviceId = pipelineIds[i]; + + /* + * Submit task on local executor. The task will do an RMI to the + * remote service. + */ + final Future<IHAPipelineResetResponse> rf = member + .getExecutor().submit( + new PipelineResetMessageTask(member, + serviceId, msg)); + + // add to list of futures we will check. + localFutures.add(rf); + + } + + { + /* + * Run the operation on the leader using a local method call + * (non-RMI) in the caller's thread to avoid deadlock. + */ + member.assertLeader(token); + final FutureTask<IHAPipelineResetResponse> ft = new FutureTask<IHAPipelineResetResponse>( + new ResetPipelineTaskImpl(msg)); + localFutures.add(ft); + ft.run();// run on the leader. + } + /* + * Check the futures for the other services in the quorum. + */ + final List<Throwable> causes = new LinkedList<Throwable>(); + for (Future<IHAPipelineResetResponse> ft : localFutures) { + try { + ft.get(); // TODO Timeout? + } catch (InterruptedException ex) { + log.error(ex, ex); + causes.add(ex); + } catch (ExecutionException ex) { + log.error(ex, ex); + causes.add(ex); + } catch (RuntimeException ex) { + /* + * Note: ClientFuture.get() can throw a RuntimeException + * if there is a problem with the RMI call. In this case + * we do not know whether the Future is done. + */ + log.error(ex, ex); + causes.add(ex); + } finally { + // Note: cancelling a *local* Future wrapping an RMI. + ft.cancel(true/* mayInterruptIfRunning */); + } + } + + /* + * If there were any errors, then throw an exception listing them. + * + * TODO But only throw an exception for the joined services. + * Non-joined services, we just long an error (or simply do not tell + * them to do an abort()). + */ + if (!causes.isEmpty()) { + // Throw exception back to the leader. + if (causes.size() == 1) + throw new RuntimeException(causes.get(0)); + throw new RuntimeException("remote errors: nfailures=" + + causes.size(), new ExecutionExceptions(causes)); + } + + } finally { + + // Ensure that all futures are cancelled. + QuorumServiceBase.cancelFutures(localFutures); + + } + + } + + static private class PipelineResetMessageTask<S extends HAPipelineGlue> + extends + AbstractMessageTask<S, IHAPipelineResetResponse, IHAPipelineResetRequest> { + + public PipelineResetMessageTask(final ServiceLookup<S> serviceLookup, + final UUID serviceId, final IHAPipelineResetRequest msg) { + + super(serviceLookup, serviceId, msg); + + } + + @Override + protected Future<IHAPipelineResetResponse> doRMI(final S service) + throws IOException { + + return service.resetPipeline(msg); + } + + } + + /** * Lock used to ensure that at most one message is being sent along the * write pipeline at a time. */ @@ -1974,7 +2202,7 @@ ft = new FutureTask<Void>(new ReceiveAndReplicateTask<S>( member, token, req, snd, msg, b, downstream, - receiveService)); + receiveService, QuorumPipelineImpl.this)); } @@ -2078,13 +2306,15 @@ private final ByteBuffer b; private final PipelineState<S> downstream; private final HAReceiveService<HAMessageWrapper> receiveService; + private final QuorumPipelineImpl<S> outerClass; public ReceiveAndReplicateTask(final QuorumMember<S> member, final long token, final IHASyncRequest req, final IHASendState snd, final IHAWriteMessage msg, final ByteBuffer b, final PipelineState<S> downstream, - final HAReceiveService<HAMessageWrapper> receiveService) { + final HAReceiveService<HAMessageWrapper> receiveService, + final QuorumPipelineImpl<S> outerClass) { this.member = member; this.token = token; @@ -2094,6 +2324,7 @@ this.b = b; this.downstream = downstream; this.receiveService = receiveService; + this.outerClass = outerClass; } @Override @@ -2159,10 +2390,11 @@ } finally { // cancel the local Future. - futRec.cancel(true/* mayInterruptIfRunning */); // FIXME Cancel hits wrong send() payload? + futRec.cancel(true/* mayInterruptIfRunning */); } } catch (Throwable t) { - launderPipelineException(false/* isLeader */, member, t); + launderPipelineException(false/* isLeader */, token, member, + outerClass, t); } // done return null; Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumServiceBase.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumServiceBase.java 2013-12-17 01:00:14 UTC (rev 7666) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumServiceBase.java 2013-12-17 17:27:53 UTC (rev 7667) @@ -29,6 +29,7 @@ import java.io.IOException; import java.nio.ByteBuffer; +import java.util.List; import java.util.UUID; import java.util.concurrent.ExecutorService; import java.util.concurrent.Future; @@ -44,6 +45,8 @@ import com.bigdata.journal.IRootBlockView; import com.bigdata.journal.Journal; import com.bigdata.quorum.AbstractQuorumMember; +import com.bigdata.service.proxy.ThickFuture; +import com.bigdata.util.InnerCause; /** * Abstract implementation provides the logic for distributing messages for the @@ -249,6 +252,14 @@ } + @Override + public Future<IHAPipelineResetResponse> resetPipeline( + IHAPipelineResetRequest req) throws IOException { + + return pipelineImpl.resetPipeline(req); + + } + /** * Core implementation handles the message and payload when received on a * service. @@ -430,4 +441,54 @@ } + /** + * Cancel the requests on the remote services (RMI). This is a best effort + * implementation. Any RMI related errors are trapped and ignored in order + * to be robust to failures in RMI when we try to cancel the futures. + * <p> + * NOte: This is not being done in parallel. However, due to a DGC thread + * leak issue, we now use {@link ThickFuture}s. Thus, the tasks that are + * being cancelled are all local tasks running on the + * {@link #executorService}. If that local task is doing an RMI, then + * cancelling it will cause an interrupt in the NIO request. + */ + public static <F extends Future<T>, T> void cancelFutures( + final List<F> futures) { + + if (log.isInfoEnabled()) + log.info(""); + + for (F f : futures) { + + if (f == null) { + + continue; + + } + + try { + + if (!f.isDone()) { + + f.cancel(true/* mayInterruptIfRunning */); + + } + + } catch (Throwable t) { + + if (InnerCause.isInnerCause(t, InterruptedException.class)) { + + // Propagate interrupt. + Thread.currentThread().interrupt(); + + } + + // ignored (to be robust). + + } + + } + + } + } Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HAReceiveService.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HAReceiveService.java 2013-12-17 01:00:14 UTC (rev 7666) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HAReceiveService.java 2013-12-17 17:27:53 UTC (rev 7667) @@ -117,9 +117,14 @@ * data to a downstream service. */ private final HASendService sendService; - - private final ExecutorService executor = Executors.newSingleThreadExecutor(); - + + public HASendService getSendService() { + return sendService; + } + + private final ExecutorService executor = Executors + .newSingleThreadExecutor(); + // private ServerSocketChannel server; // private FutureTask<Void> readFuture; Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HASendService.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HASendService.java 2013-12-17 01:00:14 UTC (rev 7666) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/pipeline/HASendService.java 2013-12-17 17:27:53 UTC (rev 7667) @@ -258,16 +258,7 @@ return; } try { - final SocketChannel socketChannel = this.socketChannel.get(); - if (socketChannel != null) { - try { - socketChannel.close(); - } catch (IOException ex) { - log.error("Ignoring exception during close: " + ex, ex); - } finally { - this.socketChannel.set(null); - } - } + closeSocketChannelNoBlock(); } finally { // shutdown executor. tmp.shutdownNow(); @@ -279,6 +270,33 @@ } /** + * Close the {@link SocketChannel} to the downsteam service (blocking). + */ + public void closeChannel() { + synchronized (this.socketChannel) { + closeSocketChannelNoBlock(); + } + } + + /** + * Close the {@link SocketChannel} to the downstream service (non-blocking). + */ + private void closeSocketChannelNoBlock() { + final SocketChannel socketChannel = this.socketChannel.get(); + if (socketChannel != null) { + try { + socketChannel.close(); + } catch (IOException ex) { + log.error("Ignoring exception during close: " + ex, ex); + } finally { + this.socketChannel.set(null); + } + if (log.isInfoEnabled()) + log.info("Closed socket channel"); + } + } + + /** * Send the bytes {@link ByteBuffer#remaining()} in the buffer to the * configured {@link InetSocketAddress}. * <p> @@ -393,7 +411,7 @@ * A series of timeouts used when we need to re-open the * {@link SocketChannel}. */ - private final static long[] retryMillis = new long[] { 1, 5, 10, 50, 100, 250, 500 }; + private final static long[] retryMillis = new long[] { 1, 5, 10, 50, 100, 250, 250, 250, 250 }; /** * (Re-)open the {@link SocketChannel} if it is closed and this service is @@ -448,12 +466,14 @@ socketChannel.set(sc = openChannel(addrNext.get())); if (log.isInfoEnabled()) - log.info("Opened channel on try: " + tryno); + log.info("Opened channel on try: " + tryno + + ", addrNext=" + addrNext); } catch (IOException e) { if (log.isInfoEnabled()) - log.info("Failed to open channel on try: " + tryno); + log.info("Failed to open channel on try: " + tryno + + ", addrNext=" + addrNext); if (tryno < retryMillis.length) { @@ -671,7 +691,7 @@ */ final int nbytes; - if (false&&log.isDebugEnabled()) { // add debug latency + if (false || log.isDebugEnabled()) { // FIXME add debug latency final int limit = data.limit(); if (data.position() < (limit - 50000)) { data.limit(data.position() + 50000); Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/journal/AbstractJournal.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/journal/AbstractJournal.java 2013-12-17 01:00:14 UTC (rev 7666) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/journal/AbstractJournal.java 2013-12-17 17:27:53 UTC (rev 7667) @@ -100,6 +100,8 @@ import com.bigdata.ha.HAGlue; import com.bigdata.ha.HAStatusEnum; import com.bigdata.ha.HATXSGlue; +import com.bigdata.ha.IHAPipelineResetRequest; +import com.bigdata.ha.IHAPipelineResetResponse; import com.bigdata.ha.IIndexManagerCallable; import com.bigdata.ha.IJoinedAndNonJoinedServices; import com.bigdata.ha.JoinedAndNonJoinedServices; @@ -8018,6 +8020,14 @@ return getProxy(ft); } + @Override + public Future<IHAPipelineResetResponse> resetPipeline( + final IHAPipelineResetRequest req) throws IOException { + final Future<IHAPipelineResetResponse> f = quorum.getClient() + .resetPipeline(req); + return getProxy(f); + } + /* * HATXSGlue. * @@ -8243,7 +8253,6 @@ } - }; /** Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/QuorumClient.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/QuorumClient.java 2013-12-17 01:00:14 UTC (rev 7666) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/QuorumClient.java 2013-12-17 17:27:53 UTC (rev 7667) @@ -41,7 +41,8 @@ * @author <a href="mailto:tho...@us...">Bryan Thompson</a> * @version $Id$ */ -public interface QuorumClient<S extends Remote> extends QuorumListener { +public interface QuorumClient<S extends Remote> extends QuorumListener, + ServiceLookup<S> { /** * The fully qualified identifier of the logical service whose quorum state Added: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/ServiceLookup.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/ServiceLookup.java (rev 0) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/quorum/ServiceLookup.java 2013-12-17 17:27:53 UTC (rev 7667) @@ -0,0 +1,51 @@ +/** + +Copyright (C) SYSTAP, LLC 2006-2010. All rights reserved. + +Contact: + SYSTAP, LLC + 4501 Tower Road + Greensboro, NC 27410 + lic...@bi... + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; version 2 of the License. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ +/* + * Created on Jun 2, 2010 + */ +package com.bigdata.quorum; + +import java.rmi.Remote; +import java.util.UUID; + +public interface ServiceLookup<S extends Remote> { + + /** + * Return the remote interface used to perform HA operations on a member of + * quorum. + * + * @param serviceId + * The {@link UUID} associated with the service. + * + * @return The remote interface for that quorum member. + * + * @throws IllegalArgumentException + * if the argument is <code>null</code> + * @throws QuorumException + * if there is no {@link Quorum} member with that + * <i>serviceId</i>. + */ + S getService(UUID serviceId); + +} Modified: branches/MGC_1_3_0/bigdata/src/test/com/bigdata/io/writecache/TestWORMWriteCacheService.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/test/com/bigdata/io/writecache/TestWORMWriteCacheService.java 2013-12-17 01:00:14 UTC (rev 7666) +++ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/io/writecache/TestWORMWriteCacheService.java 2013-12-17 17:27:53 UTC (rev 7667) @@ -49,6 +49,8 @@ import com.bigdata.ha.HAGlueBase; import com.bigdata.ha.HAPipelineGlue; +import com.bigdata.ha.IHAPipelineResetRequest; +import com.bigdata.ha.IHAPipelineResetResponse; import com.bigdata.ha.QuorumPipeline; import com.bigdata.ha.QuorumPipelineImpl; import com.bigdata.ha.msg.IHALogRequest; @@ -271,6 +273,12 @@ throw new UnsupportedOperationException(); } + @Override + public Future<IHAPipelineResetResponse> resetPipeline( + final IHAPipelineResetRequest req) throws IOException { + throw new UnsupportedOperationException(); + } + } // class MockHAPipelineGlue /** @@ -493,6 +501,12 @@ // NOP } + + @Override + public Future<IHAPipelineResetResponse> resetPipeline( + IHAPipelineResetRequest req) throws IOException { + throw new UnsupportedOperationException(); + } } // MockQuorumMemberImpl Modified: branches/MGC_1_3_0/bigdata/src/test/com/bigdata/quorum/MockQuorumFixture.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/test/com/bigdata/quorum/MockQuorumFixture.java 2013-12-17 01:00:14 UTC (rev 7666) +++ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/quorum/MockQuorumFixture.java 2013-12-17 17:27:53 UTC (rev 7667) @@ -56,6 +56,8 @@ import org.apache.log4j.Logger; import com.bigdata.ha.HAPipelineGlue; +import com.bigdata.ha.IHAPipelineResetRequest; +import com.bigdata.ha.IHAPipelineResetResponse; import com.bigdata.ha.msg.IHALogRequest; import com.bigdata.ha.msg.IHALogRootBlocksRequest; import com.bigdata.ha.msg.IHALogRootBlocksResponse; @@ -1335,6 +1337,12 @@ throw new UnsupportedOperationException(); } + @Override + public Future<IHAPipelineResetResponse> resetPipeline( + IHAPipelineResetRequest req) throws IOException { + throw new UnsupportedOperationException(); + } + } // MockService } // MockQuorumMember Modified: branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/HAJournalTest.java =================================================================== --- branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/HAJournalTest.java 2013-12-17 01:00:14 UTC (rev 7666) +++ branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/HAJournalTest.java 2013-12-17 17:27:53 UTC (rev 7667) @@ -54,6 +54,8 @@ import com.bigdata.counters.PIDUtil; import com.bigdata.ha.HAGlue; import com.bigdata.ha.HAStatusEnum; +import com.bigdata.ha.IHAPipelineResetRequest; +import com.bigdata.ha.IHAPipelineResetResponse; import com.bigdata.ha.QuorumService; import com.bigdata.ha.RunState; import com.bigdata.ha.msg.IHA2PhaseAbortMessage; @@ -1112,6 +1114,15 @@ } @Override + public Future<IHAPipelineResetResponse> resetPipeline( + final IHAPipelineResetRequest req) throws IOException { + + checkMethod("resetPipeline", new Class[] {}); + + return super.resetPipeline(req); + } + + @Override public Future<Void> receiveAndReplicate(final IHASyncRequest req, final IHASendState snd, final IHAWriteMessage msg) throws IOException { Modified: branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHAJournalServer.java =================================================================== --- branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHAJournalServer.java 2013-12-17 01:00:14 UTC (rev 7666) +++ branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHAJournalServer.java 2013-12-17 17:27:53 UTC (rev 7667) @@ -26,16 +26,27 @@ */ package com.bigdata.journal.jini.ha; +import java.io.IOException; import java.util.UUID; +import java.util.concurrent.Callable; +import java.util.concurrent.ExecutorService; +import java.util.concurrent.Executors; +import java.util.concurrent.Future; +import java.util.concurrent.FutureTask; import java.util.concurrent.TimeUnit; import java.util.concurrent.TimeoutException; +import java.util.concurrent.atomic.AtomicReference; import net.jini.config.Configuration; import net.jini.core.lookup.ServiceID; import com.bigdata.ha.HAGlue; import com.bigdata.ha.HAStatusEnum; +import com.bigdata.ha.IndexManagerCallable; import com.bigdata.ha.msg.HADigestRequest; +import com.bigdata.journal.jini.ha.HAJournalTest.HAGlueTest; +import com.bigdata.util.InnerCause; +import com.bigdata.util.concurrent.DaemonThreadFactory; /** * Life cycle and related tests for a single remote {@link HAJournalServer} out @@ -347,4 +358,153 @@ } + /** + * This test is used to characterize what happens when we interrupt an RMI. + * Most methods on the {@link HAGlue} interface are synchronous - they block + * while some behavior is executed. This is even true for some methods that + * return a {@link Future} in order to avoid overhead associated with the + * export of a proxy and DGC thread leaks (since fixed in River). + * <p> + * This unit test setups up a service and then issues an RMI that invokes a + * {@link Thread#sleep(long)} method on the service. The thread that issues + * the RMI is then interrupted during the sleep. + * + * @throws Exception + */ + public void test_interruptRMI() throws Exception { + + // Start a service. + final HAGlue serverA = startA(); + + final AtomicReference<Throwable> localCause = new AtomicReference<Throwable>(); + + final ExecutorService executorService = Executors + .newSingleThreadScheduledExecutor(DaemonThreadFactory + .defaultThreadFactory()); + + try { + + final FutureTask<Void> localFuture = new FutureTask<Void>( + new Callable<Void>() { + + @Override + public Void call() throws Exception { + + try { + final Future<Void> ft = ((HAGlueTest) serverA) + .submit(new SleepTask(6000/* ms */), + false/* asyncFuture */); + + return ft.get(); + } catch (Throwable t) { + localCause.set(t); + log.error(t, t); + throw new RuntimeException(t); + } finally { + log.warn("Local submit of remote task is done."); + } + } + }); + /* + * Submit task that will execute sleep on A. This task will block + * until A finishes its sleep. When we cancel this task, the RMI to + * A will be interrupted. + */ + executorService.execute(localFuture); + + // Wait a bit to ensure that the task was started on A. + Thread.sleep(2000/* ms */); + + // interrupt the local future. will cause interrupt of the RMI. + localFuture.cancel(true/*mayInterruptIfRunning*/); + + } finally { + + executorService.shutdownNow(); + + } + + /* + * The local root cause of the RMI failure is an InterruptedException. + * + * Note: There is a data race between when the [localCause] is set and + * when we exit the code block above. This is because we are + * interrupting the local task and have no means to await the completion + * of its error handling routine which sets the [localCause]. + */ + { + assertCondition(new Runnable() { + @Override + public void run() { + final Throwable tmp = localCause.get(); + assertNotNull(tmp); + assertTrue(InnerCause.isInnerCause(tmp, + InterruptedException.class)); + } + }, 10000/*timeout*/, TimeUnit.MILLISECONDS); + } + + /* + * Verify the root cause as observed by A for the interrupt. It should + * also be an InterruptedException. + * + * Note: Again, there is a data race. + * + * Note: Because we might retry this, we do NOT use the getAndClearXXX() + * method to recover the remote exception. + */ + { + assertCondition(new Runnable() { + @Override + public void run() { + Throwable tmp; + try { + tmp = ((HAGlueTest) serverA).getLastRootCause(); + } catch (IOException e) { + throw new RuntimeException(e); + } + assertNotNull(tmp); + log.warn("Received non-null lastRootCause=" + tmp, tmp); + assertTrue(InnerCause.isInnerCause(tmp, + InterruptedException.class)); + } + }, 10000/* timeout */, TimeUnit.MILLISECONDS); + } + + } + + /** + * Task sleeps for a specified duration. + * + * @author <a href="mailto:tho...@us...">Bryan + * Thompson</a> + */ + private static class SleepTask extends IndexManagerCallable<Void> { + + private static final long serial... [truncated message content] |
From: <tho...@us...> - 2013-12-17 18:00:50
|
Revision: 7668 http://bigdata.svn.sourceforge.net/bigdata/?rev=7668&view=rev Author: thompsonbry Date: 2013-12-17 18:00:44 +0000 (Tue, 17 Dec 2013) Log Message: ----------- Sync to martyn. See #724. Modified Paths: -------------- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/HAJournalTest.java Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java 2013-12-17 17:27:53 UTC (rev 7667) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/ha/QuorumPipelineImpl.java 2013-12-17 18:00:44 UTC (rev 7668) @@ -1237,7 +1237,7 @@ // FIXME Versus using the inner handler? // innerEventHandler.pipelineUpstreamChange(); // innerEventHandler.pipelineChange(oldDownStreamId, newDownStreamId); - + log.warn("Will reset pipeline"); if (receiveService != null) { receiveService.changeUpStream(); @@ -1755,7 +1755,7 @@ final IHAWriteMessage msg, final ByteBuffer b, final PipelineState<S> downstream, final HASendService sendService, - final QuorumPipelineImpl outerClass, final Lock sendLock) { + final QuorumPipelineImpl<S> outerClass, final Lock sendLock) { this.member = member; this.token = token; @@ -1873,7 +1873,7 @@ */ static private <S extends HAPipelineGlue> void launderPipelineException( final boolean isLeader, final long token, - final QuorumMember<S> member, final QuorumPipelineImpl outerClass, + final QuorumMember<S> member, final QuorumPipelineImpl<S> outerClass, final Throwable t) { log.warn("isLeader=" + isLeader + ", t=" + t, t); @@ -1904,23 +1904,29 @@ member.getServiceId()); if (isLeader) { + + // The problem service (iff identified). + UUID problemServiceId = null; try { - + /* * If we can identify the problem service, then force it out of * the pipeline. It can re-enter the pipeline once it * transitions through its ERROR state. */ + if (directCause != null) { - member.getActor().forceRemoveService(priorAndNext[1]); + problemServiceId = priorAndNext[1]; + + member.getActor().forceRemoveService(problemServiceId); } else if (remoteCause != null) { - final UUID problemService = remoteCause.getProblemServiceId(); + problemServiceId = remoteCause.getProblemServiceId(); - member.getActor().forceRemoveService(problemService); + member.getActor().forceRemoveService(problemServiceId); } else { @@ -1928,28 +1934,46 @@ } - /** - * Reset the pipeline on each service (including the leader). If - * replication fails, the socket connections both upstream and - * downstream of the point of failure can be left in an - * indeterminate state with partially buffered data. In order to - * bring the pipeline back into a known state (without forcing a - * quorum break) we message each service in the pipeline to - * reset its HAReceiveService (including the inner - * HASendService. The next message and payload relayed from the - * leader will cause new socket connections to be established. - * - * @see <a - * href="https://sourceforge.net/apps/trac/bigdata/ticket/724" - * > HA Wire Pulling and Sudden Kills </a> - */ - outerClass.resetPipeline(token); + } catch (Throwable e) { + + // Log and continue. + log.error("Problem on node removal", e); - } catch (Exception e) { + if(InnerCause.isInnerCause(t, InterruptedException.class)) { + // Propagate interrupt. + Thread.currentThread().interrupt(); + } - log.error("Problem on node removal", e); + } - throw new RuntimeException(e); + /** + * Reset the pipeline on each service (including the leader). If + * replication fails, the socket connections both upstream and + * downstream of the point of failure can be left in an + * indeterminate state with partially buffered data. In order to + * bring the pipeline back into a known state (without forcing a + * quorum break) we message each service in the pipeline to reset + * its HAReceiveService (including the inner HASendService. The next + * message and payload relayed from the leader will cause new socket + * connections to be established. + * + * @see <a + * href="https://sourceforge.net/apps/trac/bigdata/ticket/724" + * > HA Wire Pulling and Sudden Kills </a> + */ + try { + + outerClass.resetPipeline(token, problemServiceId); + + } catch (Throwable e) { + + // Log and continue. + log.error("Problem on reset pipeline", e); + + if(InnerCause.isInnerCause(t, InterruptedException.class)) { + // Propagate interrupt. + Thread.currentThread().interrupt(); + } } @@ -1980,9 +2004,10 @@ * * @param token * The quorum token on the leader. - * @param member + * @param problemServiceId + * The problem service in the write pipeline (if known). */ - private void resetPipeline(final long token) { + private void resetPipeline(final long token, final UUID problemServiceId) { log.error("Leader will reset pipeline: " + token); @@ -2019,7 +2044,7 @@ */ final Future<IHAPipelineResetResponse> rf = member .getExecutor().submit( - new PipelineResetMessageTask(member, + new PipelineResetMessageTask<S>(member, serviceId, msg)); // add to list of futures we will check. @@ -2067,10 +2092,6 @@ /* * If there were any errors, then throw an exception listing them. - * - * TODO But only throw an exception for the joined services. - * Non-joined services, we just long an error (or simply do not tell - * them to do an abort()). */ if (!causes.isEmpty()) { // Throw exception back to the leader. Modified: branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/HAJournalTest.java =================================================================== --- branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/HAJournalTest.java 2013-12-17 17:27:53 UTC (rev 7667) +++ branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/HAJournalTest.java 2013-12-17 18:00:44 UTC (rev 7668) @@ -1117,7 +1117,7 @@ public Future<IHAPipelineResetResponse> resetPipeline( final IHAPipelineResetRequest req) throws IOException { - checkMethod("resetPipeline", new Class[] {}); + checkMethod("resetPipeline", new Class[] {IHAPipelineResetRequest.class}); return super.resetPipeline(req); } This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |
From: <tho...@us...> - 2013-12-19 21:34:42
|
Revision: 7685 http://bigdata.svn.sourceforge.net/bigdata/?rev=7685&view=rev Author: thompsonbry Date: 2013-12-19 21:34:30 +0000 (Thu, 19 Dec 2013) Log Message: ----------- Merging in changes from the main development branch. This will catch up the feature branch with the 1.3.0 release. Among other things, this will clear up CI quite a bit. Note: The HASendService will not use small chunks in this commit - the code is there, but it needs to be enabled by hand for debuging. At revision r7684 in MGC_1_3_0. {{{ merge https://bigdata.svn.sourceforge.net/svnroot/bigdata/branches/BIGDATA_RELEASE_1_3_0 /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC --- Merging r7607 through r7684 into /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHAJournalServer.java U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHAJournalServerOverride.java U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHA3ChangeLeader.java U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-jini/src/java/com/bigdata/quorum/zk/ZKQuorumImpl.java U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-jini/src/java/com/bigdata/journal/jini/ha/HAJournalServer.java U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-jini/src/java/com/bigdata/journal/jini/ha/NoSnapshotPolicy.java U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-jini/src/java/com/bigdata/journal/jini/ha/HAJournal.java U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-jini/src/java/com/bigdata/journal/jini/ha/DefaultSnapshotPolicy.java U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/build.properties U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-war/src/html/index.html U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata/src/test/com/bigdata/quorum/MockQuorumFixture.java U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata/src/test/com/bigdata/io/TestNameAndExtensionFilter.java C /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata/src/java/com/bigdata/quorum/AbstractQuorum.java C /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata/src/java/com/bigdata/quorum/QuorumActor.java U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata/src/releases/RELEASE_1_3_0.txt U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-sails/src/test/com/bigdata/rdf/sail/tck/BigdataSparqlTest.java U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-sails/src/test/com/bigdata/rdf/sail/sparql/TestReificationDoneRightParser.java --- Merging r7607 through r7684 into /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-sails/src/java/com/bigdata/rdf/sail/webapp U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-sails/src/java/com/bigdata/rdf/sail/webapp/HAStatusServletUtil.java U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-sails/src/java/com/bigdata/rdf/sail/webapp/InsertServlet.java --- Merging r7607 through r7684 into /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-sails/src/java/com/bigdata/rdf/sail/sparql/PrefixDeclProcessor.java U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-rdf/src/test/com/bigdata/rdf/store/TestLocalTripleStoreWithoutStatementIdentifiers.java U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/reif/rdr-01a.rq U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/reif/TestReificationDoneRightEval.java U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/reif/rdr-03a.rq U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/reif/rdr-01.ttl U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/reif/rdr-03.ttl U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/reif/rdr-02a.ttl U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/reif/rdr-03a.ttl U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-rdf/src/java/com/bigdata/rdf/rio/StatementBuffer.java U /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/QueryHints.java Merge complete. ===== File Statistics: ===== Updated: 28 ==== Conflict Statistics: ===== File conflicts: 2 }}} For both AbstractQuorum and QuorumActor, the conflicts were resolved by using the versions from the feature branch (MGC_1_3_0). See #779 Revision Links: -------------- http://bigdata.svn.sourceforge.net/bigdata/?rev=7684&view=rev http://bigdata.svn.sourceforge.net/bigdata/?rev=7607&view=rev http://bigdata.svn.sourceforge.net/bigdata/?rev=7684&view=rev http://bigdata.svn.sourceforge.net/bigdata/?rev=7607&view=rev http://bigdata.svn.sourceforge.net/bigdata/?rev=7684&view=rev http://bigdata.svn.sourceforge.net/bigdata/?rev=7607&view=rev http://bigdata.svn.sourceforge.net/bigdata/?rev=7684&view=rev Modified Paths: -------------- branches/MGC_1_3_0/bigdata/src/releases/RELEASE_1_3_0.txt branches/MGC_1_3_0/bigdata/src/test/com/bigdata/io/TestNameAndExtensionFilter.java branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/journal/jini/ha/DefaultSnapshotPolicy.java branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/journal/jini/ha/HAJournal.java branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/journal/jini/ha/HAJournalServer.java branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/journal/jini/ha/NoSnapshotPolicy.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHA3ChangeLeader.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHAJournalServer.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHAJournalServerOverride.java branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/reif/TestReificationDoneRightEval.java branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/reif/rdr-01.ttl branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/reif/rdr-01a.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/reif/rdr-02a.ttl branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/reif/rdr-03.ttl branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/reif/rdr-03a.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/reif/rdr-03a.ttl branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/store/TestLocalTripleStoreWithoutStatementIdentifiers.java branches/MGC_1_3_0/bigdata-sails/src/java/com/bigdata/rdf/sail/sparql/PrefixDeclProcessor.java branches/MGC_1_3_0/bigdata-sails/src/java/com/bigdata/rdf/sail/webapp/HAStatusServletUtil.java branches/MGC_1_3_0/bigdata-sails/src/java/com/bigdata/rdf/sail/webapp/InsertServlet.java branches/MGC_1_3_0/bigdata-sails/src/test/com/bigdata/rdf/sail/sparql/TestReificationDoneRightParser.java branches/MGC_1_3_0/bigdata-sails/src/test/com/bigdata/rdf/sail/tck/BigdataSparqlTest.java branches/MGC_1_3_0/bigdata-war/src/html/index.html branches/MGC_1_3_0/build.properties Property Changed: ---------------- branches/MGC_1_3_0/ branches/MGC_1_3_0/bigdata/lib/jetty/ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/aggregate/ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/joinGraph/ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/util/ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/htree/raba/ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/jsr166/ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/bop/joinGraph/ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/bop/util/ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/jsr166/ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/util/httpd/ branches/MGC_1_3_0/bigdata-compatibility/ branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/attr/ branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/disco/ branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/util/config/ branches/MGC_1_3_0/bigdata-perf/ branches/MGC_1_3_0/bigdata-perf/btc/ branches/MGC_1_3_0/bigdata-perf/btc/src/resources/ branches/MGC_1_3_0/bigdata-perf/lubm/ branches/MGC_1_3_0/bigdata-perf/uniprot/ branches/MGC_1_3_0/bigdata-perf/uniprot/src/ branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/bop/rdf/aggregate/ branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/changesets/ branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/error/ branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/internal/ branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/relation/ branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/util/ branches/MGC_1_3_0/bigdata-rdf/src/samples/ branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/bop/rdf/aggregate/ branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/internal/ branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/relation/ branches/MGC_1_3_0/bigdata-sails/src/java/com/bigdata/rdf/sail/bench/ branches/MGC_1_3_0/bigdata-sails/src/java/com/bigdata/rdf/sail/changesets/ branches/MGC_1_3_0/bigdata-sails/src/java/com/bigdata/rdf/sail/webapp/ branches/MGC_1_3_0/bigdata-sails/src/test/com/bigdata/rdf/sail/bench/ branches/MGC_1_3_0/bigdata-sails/src/test/com/bigdata/rdf/sail/webapp/ branches/MGC_1_3_0/dsi-utils/ branches/MGC_1_3_0/dsi-utils/LEGAL/ branches/MGC_1_3_0/dsi-utils/lib/ branches/MGC_1_3_0/dsi-utils/src/ branches/MGC_1_3_0/dsi-utils/src/java/ branches/MGC_1_3_0/dsi-utils/src/java/it/ branches/MGC_1_3_0/dsi-utils/src/java/it/unimi/ branches/MGC_1_3_0/dsi-utils/src/test/ branches/MGC_1_3_0/dsi-utils/src/test/it/unimi/ branches/MGC_1_3_0/dsi-utils/src/test/it/unimi/dsi/ branches/MGC_1_3_0/lgpl-utils/src/java/it/unimi/dsi/fastutil/bytes/custom/ branches/MGC_1_3_0/lgpl-utils/src/test/it/unimi/dsi/fastutil/bytes/custom/ branches/MGC_1_3_0/osgi/ branches/MGC_1_3_0/src/resources/bin/config/ Property changes on: branches/MGC_1_3_0 ___________________________________________________________________ Modified: svn:mergeinfo - /branches/BIGDATA_OPENRDF_2_6_9_UPDATE:6769-6785 /branches/BIGDATA_RELEASE_1_2_0:6766-7380 /branches/BTREE_BUFFER_BRANCH:2004-2045 /branches/DEV_BRANCH_27_OCT_2009:2270-2546,2548-2782 /branches/INT64_BRANCH:4486-4522 /branches/JOURNAL_HA_BRANCH:2596-4066 /branches/LARGE_LITERALS_REFACTOR:4175-4387 /branches/LEXICON_REFACTOR_BRANCH:2633-3304 /branches/QUADS_QUERY_BRANCH:4525-4531,4550-4584,4586-4609,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE:7215-7271 /branches/RWSTORE_1_1_0_DEBUG:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH:4814-4836 /branches/ZK_DISCONNECT_HANDLING:7465-7484 /branches/bugfix-btm:2594-3237 /branches/dev-btm:2574-2730 /branches/fko:3150-3194 /trunk:3392-3437,3656-4061 + /branches/BIGDATA_OPENRDF_2_6_9_UPDATE:6769-6785 /branches/BIGDATA_RELEASE_1_2_0:6766-7380 /branches/BIGDATA_RELEASE_1_3_0:7608-7684 /branches/BTREE_BUFFER_BRANCH:2004-2045 /branches/DEV_BRANCH_27_OCT_2009:2270-2546,2548-2782 /branches/INT64_BRANCH:4486-4522 /branches/JOURNAL_HA_BRANCH:2596-4066 /branches/LARGE_LITERALS_REFACTOR:4175-4387 /branches/LEXICON_REFACTOR_BRANCH:2633-3304 /branches/QUADS_QUERY_BRANCH:4525-4531,4550-4584,4586-4609,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE:7215-7271 /branches/RWSTORE_1_1_0_DEBUG:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH:4814-4836 /branches/ZK_DISCONNECT_HANDLING:7465-7484 /branches/bugfix-btm:2594-3237 /branches/dev-btm:2574-2730 /branches/fko:3150-3194 /trunk:3392-3437,3656-4061 Property changes on: branches/MGC_1_3_0/bigdata/lib/jetty ___________________________________________________________________ Modified: svn:mergeinfo - /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/lib/jetty:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/lib/jetty:6766-7380 /branches/INT64_BRANCH/bigdata/lib/jetty:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/lib/jetty:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/lib/jetty:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/lib/jetty:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/lib/jetty:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/lib/jetty:7465-7484 + /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/lib/jetty:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/lib/jetty:6766-7380 /branches/BIGDATA_RELEASE_1_3_0/bigdata/lib/jetty:7608-7684 /branches/INT64_BRANCH/bigdata/lib/jetty:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/lib/jetty:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/lib/jetty:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/lib/jetty:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/lib/jetty:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/lib/jetty:7465-7484 Property changes on: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/aggregate ___________________________________________________________________ Modified: svn:mergeinfo - /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/src/java/com/bigdata/bop/aggregate:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/src/java/com/bigdata/bop/aggregate:6766-7380 /branches/INT64_BRANCH/bigdata/src/java/com/bigdata/bop/aggregate:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/src/java/com/bigdata/bop/aggregate:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/src/java/com/bigdata/bop/aggregate:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/src/java/com/bigdata/bop/aggregate:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/src/java/com/bigdata/bop/aggregate:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/src/java/com/bigdata/bop/aggregate:7465-7484 + /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/src/java/com/bigdata/bop/aggregate:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/src/java/com/bigdata/bop/aggregate:6766-7380 /branches/BIGDATA_RELEASE_1_3_0/bigdata/src/java/com/bigdata/bop/aggregate:7608-7684 /branches/INT64_BRANCH/bigdata/src/java/com/bigdata/bop/aggregate:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/src/java/com/bigdata/bop/aggregate:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/src/java/com/bigdata/bop/aggregate:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/src/java/com/bigdata/bop/aggregate:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/src/java/com/bigdata/bop/aggregate:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/src/java/com/bigdata/bop/aggregate:7465-7484 Property changes on: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/joinGraph ___________________________________________________________________ Modified: svn:mergeinfo - /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/src/java/com/bigdata/bop/joinGraph:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/src/java/com/bigdata/bop/joinGraph:6766-7380 /branches/INT64_BRANCH/bigdata/src/java/com/bigdata/bop/joinGraph:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/src/java/com/bigdata/bop/joinGraph:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/src/java/com/bigdata/bop/joinGraph:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/src/java/com/bigdata/bop/joinGraph:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/src/java/com/bigdata/bop/joinGraph:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/src/java/com/bigdata/bop/joinGraph:7465-7484 + /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/src/java/com/bigdata/bop/joinGraph:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/src/java/com/bigdata/bop/joinGraph:6766-7380 /branches/BIGDATA_RELEASE_1_3_0/bigdata/src/java/com/bigdata/bop/joinGraph:7608-7684 /branches/INT64_BRANCH/bigdata/src/java/com/bigdata/bop/joinGraph:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/src/java/com/bigdata/bop/joinGraph:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/src/java/com/bigdata/bop/joinGraph:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/src/java/com/bigdata/bop/joinGraph:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/src/java/com/bigdata/bop/joinGraph:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/src/java/com/bigdata/bop/joinGraph:7465-7484 Property changes on: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/util ___________________________________________________________________ Modified: svn:mergeinfo - /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/src/java/com/bigdata/bop/util:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/src/java/com/bigdata/bop/util:6766-7380 /branches/INT64_BRANCH/bigdata/src/java/com/bigdata/bop/util:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/src/java/com/bigdata/bop/util:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/src/java/com/bigdata/bop/util:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/src/java/com/bigdata/bop/util:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/src/java/com/bigdata/bop/util:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/src/java/com/bigdata/bop/util:7465-7484 + /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/src/java/com/bigdata/bop/util:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/src/java/com/bigdata/bop/util:6766-7380 /branches/BIGDATA_RELEASE_1_3_0/bigdata/src/java/com/bigdata/bop/util:7608-7684 /branches/INT64_BRANCH/bigdata/src/java/com/bigdata/bop/util:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/src/java/com/bigdata/bop/util:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/src/java/com/bigdata/bop/util:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/src/java/com/bigdata/bop/util:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/src/java/com/bigdata/bop/util:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/src/java/com/bigdata/bop/util:7465-7484 Property changes on: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/htree/raba ___________________________________________________________________ Modified: svn:mergeinfo - /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/src/java/com/bigdata/htree/raba:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/src/java/com/bigdata/htree/raba:6766-7380 /branches/INT64_BRANCH/bigdata/src/java/com/bigdata/htree/raba:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/src/java/com/bigdata/htree/raba:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/src/java/com/bigdata/htree/raba:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/src/java/com/bigdata/htree/raba:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/src/java/com/bigdata/htree/raba:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/src/java/com/bigdata/htree/raba:7465-7484 + /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/src/java/com/bigdata/htree/raba:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/src/java/com/bigdata/htree/raba:6766-7380 /branches/BIGDATA_RELEASE_1_3_0/bigdata/src/java/com/bigdata/htree/raba:7608-7684 /branches/INT64_BRANCH/bigdata/src/java/com/bigdata/htree/raba:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/src/java/com/bigdata/htree/raba:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/src/java/com/bigdata/htree/raba:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/src/java/com/bigdata/htree/raba:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/src/java/com/bigdata/htree/raba:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/src/java/com/bigdata/htree/raba:7465-7484 Property changes on: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/jsr166 ___________________________________________________________________ Modified: svn:mergeinfo - /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/src/java/com/bigdata/jsr166:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/src/java/com/bigdata/jsr166:6766-7380 /branches/INT64_BRANCH/bigdata/src/java/com/bigdata/jsr166:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/src/java/com/bigdata/jsr166:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/src/java/com/bigdata/jsr166:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/src/java/com/bigdata/jsr166:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/src/java/com/bigdata/jsr166:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/src/java/com/bigdata/jsr166:7465-7484 + /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/src/java/com/bigdata/jsr166:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/src/java/com/bigdata/jsr166:6766-7380 /branches/BIGDATA_RELEASE_1_3_0/bigdata/src/java/com/bigdata/jsr166:7608-7684 /branches/INT64_BRANCH/bigdata/src/java/com/bigdata/jsr166:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/src/java/com/bigdata/jsr166:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/src/java/com/bigdata/jsr166:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/src/java/com/bigdata/jsr166:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/src/java/com/bigdata/jsr166:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/src/java/com/bigdata/jsr166:7465-7484 Modified: branches/MGC_1_3_0/bigdata/src/releases/RELEASE_1_3_0.txt =================================================================== --- branches/MGC_1_3_0/bigdata/src/releases/RELEASE_1_3_0.txt 2013-12-19 21:11:18 UTC (rev 7684) +++ branches/MGC_1_3_0/bigdata/src/releases/RELEASE_1_3_0.txt 2013-12-19 21:34:30 UTC (rev 7685) @@ -1,4 +1,4 @@ -This is a minor release of bigdata(R). +This is a major release of bigdata(R). Bigdata is a horizontally-scaled, open-source architecture for indexed data with an emphasis on RDF capable of loading 1B triples in under one hour on a 15 node cluster. Bigdata operates in both a single machine mode (Journal), highly available replication cluster mode (HAJournalServer), and a horizontally sharded cluster mode (BigdataFederation). The Journal provides fast scalable ACID indexed storage for very large data sets, up to 50 billion triples / quads. The HAJournalServer adds replication, online backup, horizontal scaling of query, and high availability. The federation provides fast scalable shard-wise parallel indexed storage using dynamic sharding and shard-wise ACID updates and incremental cluster size growth. Both platforms support fully concurrent readers with snapshot isolation. @@ -8,8 +8,10 @@ Starting with the 1.0.0 release, we offer a WAR artifact [8] for easy installation of the single machine RDF database. For custom development and cluster installations we recommend checking out the code from SVN using the tag for this release. The code will build automatically under eclipse. You can also build the code using the ant script. The cluster installer requires the use of the ant script. -You can download the WAR from: +Starting with the 1.3.0 release, we offer a tarball artifact [10] for easy installation of the HA replication cluster. +You can download the WAR (standalone) or HA artifacts from: + http://sourceforge.net/projects/bigdata/ You can checkout this release from: @@ -18,16 +20,15 @@ New features: -- SPARQL 1.1 Update Extensions (SPARQL UPDATE for named solution sets). See https://sourceforge.net/apps/mediawiki/bigdata/index.php?title=SPARQL_Update for more information. -- SPARQL 1.1 Property Paths. -- Remote Java client for Multi-Tenancy extensions NanoSparqlServer -- Sesame 2.6.10 dependency +- High availability [10]. +- Property Path performance enhancements. - Plus numerous other bug fixes and performance enhancements. Feature summary: +- Highly Available Replication Clusters (HAJournalServer [10]) - Single machine data storage to ~50B triples/quads (RWStore); -- Clustered data storage is essentially unlimited; +- Clustered data storage is essentially unlimited (BigdataFederation); - Simple embedded and/or webapp deployment (NanoSparqlServer); - Triples, quads, or triples with provenance (SIDs); - Fast RDFS+ inference and truth maintenance; @@ -37,14 +38,94 @@ Road map [3]: -- High availability for the journal and the cluster. -- Runtime Query Optimizer for Analytic Query mode; and -- Simplified deployment, configuration, and administration for clusters. +- RDF Graph Mining API [12]; +- Reification Done Right [11]; +- Column-wise indexing; +- Runtime Query Optimizer for Analytic Query mode; +- Performance optimization for scale-out clusters; and +- Simplified deployment, configuration, and administration for scale-out clusters. Change log: Note: Versions with (*) MAY require data migration. For details, see [9]. +1.3.0: + +- http://sourceforge.net/apps/trac/bigdata/ticket/530 (Journal HA) +- http://sourceforge.net/apps/trac/bigdata/ticket/621 (Coalesce write cache records and install reads in cache) +- http://sourceforge.net/apps/trac/bigdata/ticket/623 (HA TXS) +- http://sourceforge.net/apps/trac/bigdata/ticket/639 (Remove triple-buffering in RWStore) +- http://sourceforge.net/apps/trac/bigdata/ticket/645 (HA backup) +- http://sourceforge.net/apps/trac/bigdata/ticket/646 (River not compatible with newer 1.6.0 and 1.7.0 JVMs) +- http://sourceforge.net/apps/trac/bigdata/ticket/648 (Add a custom function to use full text index for filtering.) +- http://sourceforge.net/apps/trac/bigdata/ticket/651 (RWS test failure) +- http://sourceforge.net/apps/trac/bigdata/ticket/652 (Compress write cache blocks for replication and in HALogs) +- http://sourceforge.net/apps/trac/bigdata/ticket/662 (Latency on followers during commit on leader) +- http://sourceforge.net/apps/trac/bigdata/ticket/663 (Issue with OPTIONAL blocks) +- http://sourceforge.net/apps/trac/bigdata/ticket/664 (RWStore needs post-commit protocol) +- http://sourceforge.net/apps/trac/bigdata/ticket/665 (HA3 LOAD non-responsive with node failure) +- http://sourceforge.net/apps/trac/bigdata/ticket/666 (Occasional CI deadlock in HALogWriter testConcurrentRWWriterReader) +- http://sourceforge.net/apps/trac/bigdata/ticket/670 (Accumulating HALog files cause latency for HA commit) +- http://sourceforge.net/apps/trac/bigdata/ticket/671 (Query on follower fails during UPDATE on leader) +- http://sourceforge.net/apps/trac/bigdata/ticket/673 (DGC in release time consensus protocol causes native thread leak in HAJournalServer at each commit) +- http://sourceforge.net/apps/trac/bigdata/ticket/674 (WCS write cache compaction causes errors in RWS postHACommit()) +- http://sourceforge.net/apps/trac/bigdata/ticket/676 (Bad patterns for timeout computations) +- http://sourceforge.net/apps/trac/bigdata/ticket/677 (HA deadlock under UPDATE + QUERY) +- http://sourceforge.net/apps/trac/bigdata/ticket/678 (DGC Thread and Open File Leaks: sendHALogForWriteSet()) +- http://sourceforge.net/apps/trac/bigdata/ticket/679 (HAJournalServer can not restart due to logically empty log file) +- http://sourceforge.net/apps/trac/bigdata/ticket/681 (HAJournalServer deadlock: pipelineRemove() and getLeaderId()) +- http://sourceforge.net/apps/trac/bigdata/ticket/684 (Optimization with skos altLabel) +- http://sourceforge.net/apps/trac/bigdata/ticket/686 (Consensus protocol does not detect clock skew correctly) +- http://sourceforge.net/apps/trac/bigdata/ticket/687 (HAJournalServer Cache not populated) +- http://sourceforge.net/apps/trac/bigdata/ticket/689 (Missing URL encoding in RemoteRepositoryManager) +- http://sourceforge.net/apps/trac/bigdata/ticket/690 (Error when using the alias "a" instead of rdf:type for a multipart insert) +- http://sourceforge.net/apps/trac/bigdata/ticket/691 (Failed to re-interrupt thread in HAJournalServer) +- http://sourceforge.net/apps/trac/bigdata/ticket/692 (Failed to re-interrupt thread) +- http://sourceforge.net/apps/trac/bigdata/ticket/693 (OneOrMorePath SPARQL property path expression ignored) +- http://sourceforge.net/apps/trac/bigdata/ticket/694 (Transparently cancel update/query in RemoteRepository) +- http://sourceforge.net/apps/trac/bigdata/ticket/695 (HAJournalServer reports "follower" but is in SeekConsensus and is not participating in commits.) +- http://sourceforge.net/apps/trac/bigdata/ticket/701 (Problems in BackgroundTupleResult) +- http://sourceforge.net/apps/trac/bigdata/ticket/702 (InvocationTargetException on /namespace call) +- http://sourceforge.net/apps/trac/bigdata/ticket/704 (ask does not return json) +- http://sourceforge.net/apps/trac/bigdata/ticket/705 (Race between QueryEngine.putIfAbsent() and shutdownNow()) +- http://sourceforge.net/apps/trac/bigdata/ticket/706 (MultiSourceSequentialCloseableIterator.nextSource() can throw NPE) +- http://sourceforge.net/apps/trac/bigdata/ticket/707 (BlockingBuffer.close() does not unblock threads) +- http://sourceforge.net/apps/trac/bigdata/ticket/708 (BIND heisenbug - race condition on select query with BIND) +- http://sourceforge.net/apps/trac/bigdata/ticket/711 (sparql protocol: mime type application/sparql-query) +- http://sourceforge.net/apps/trac/bigdata/ticket/712 (SELECT ?x { OPTIONAL { ?x eg:doesNotExist eg:doesNotExist } } incorrect) +- http://sourceforge.net/apps/trac/bigdata/ticket/715 (Interrupt of thread submitting a query for evaluation does not always terminate the AbstractRunningQuery) +- http://sourceforge.net/apps/trac/bigdata/ticket/716 (Verify that IRunningQuery instances (and nested queries) are correctly cancelled when interrupted) +- http://sourceforge.net/apps/trac/bigdata/ticket/718 (HAJournalServer needs to handle ZK client connection loss) +- http://sourceforge.net/apps/trac/bigdata/ticket/720 (HA3 simultaneous service start failure) +- http://sourceforge.net/apps/trac/bigdata/ticket/723 (HA asynchronous tasks must be canceled when invariants are changed) +- http://sourceforge.net/apps/trac/bigdata/ticket/725 (FILTER EXISTS in subselect) +- http://sourceforge.net/apps/trac/bigdata/ticket/726 (Logically empty HALog for committed transaction) +- http://sourceforge.net/apps/trac/bigdata/ticket/727 (DELETE/INSERT fails with OPTIONAL non-matching WHERE) +- http://sourceforge.net/apps/trac/bigdata/ticket/728 (Refactor to create HAClient) +- http://sourceforge.net/apps/trac/bigdata/ticket/729 (ant bundleJar not working) +- http://sourceforge.net/apps/trac/bigdata/ticket/731 (CBD and Update leads to 500 status code) +- http://sourceforge.net/apps/trac/bigdata/ticket/732 (describe statement limit does not work) +- http://sourceforge.net/apps/trac/bigdata/ticket/733 (Range optimizer not optimizing Slice service) +- http://sourceforge.net/apps/trac/bigdata/ticket/734 (two property paths interfere) +- http://sourceforge.net/apps/trac/bigdata/ticket/736 (MIN() malfunction) +- http://sourceforge.net/apps/trac/bigdata/ticket/737 (class cast exception) +- http://sourceforge.net/apps/trac/bigdata/ticket/739 (Inconsistent treatment of bind and optional property path) +- http://sourceforge.net/apps/trac/bigdata/ticket/741 (ctc-striterators should build as independent top-level project (Apache2)) +- http://sourceforge.net/apps/trac/bigdata/ticket/743 (AbstractTripleStore.destroy() does not filter for correct prefix) +- http://sourceforge.net/apps/trac/bigdata/ticket/746 (Assertion error) +- http://sourceforge.net/apps/trac/bigdata/ticket/747 (BOUND bug) +- http://sourceforge.net/apps/trac/bigdata/ticket/748 (incorrect join with subselect renaming vars) +- http://sourceforge.net/apps/trac/bigdata/ticket/754 (Failure to setup SERVICE hook and changeLog for Unisolated and Read/Write connections) +- http://sourceforge.net/apps/trac/bigdata/ticket/755 (Concurrent QuorumActors can interfere leading to failure to progress) +- http://sourceforge.net/apps/trac/bigdata/ticket/756 (order by and group_concat) +- http://sourceforge.net/apps/trac/bigdata/ticket/760 (Code review on 2-phase commit protocol) +- http://sourceforge.net/apps/trac/bigdata/ticket/764 (RESYNC failure (HA)) +- http://sourceforge.net/apps/trac/bigdata/ticket/770 (alpp ordering) +- http://sourceforge.net/apps/trac/bigdata/ticket/772 (Query timeout only checked at operator start/stop.) +- http://sourceforge.net/apps/trac/bigdata/ticket/776 (Closed as duplicate of #490) +- http://sourceforge.net/apps/trac/bigdata/ticket/778 (HA Leader fail results in transient problem with allocations on other services) +- http://sourceforge.net/apps/trac/bigdata/ticket/783 (Operator Alerts (HA)) + 1.2.4: - http://sourceforge.net/apps/trac/bigdata/ticket/777 (ConcurrentModificationException in ASTComplexOptionalOptimizer) @@ -293,6 +374,9 @@ [7] http://www.systap.com/bigdata.htm [8] http://sourceforge.net/projects/bigdata/files/bigdata/ [9] http://sourceforge.net/apps/mediawiki/bigdata/index.php?title=DataMigration +[10] http://sourceforge.net/apps/mediawiki/bigdata/index.php?title=HAJournalServer +[11] http://www.bigdata.com/whitepapers/reifSPARQL.pdf +[12] http://sourceforge.net/apps/mediawiki/bigdata/index.php?title=RDF_GAS_API About bigdata: Property changes on: branches/MGC_1_3_0/bigdata/src/test/com/bigdata/bop/joinGraph ___________________________________________________________________ Modified: svn:mergeinfo - /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/src/test/com/bigdata/bop/joinGraph:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/src/test/com/bigdata/bop/joinGraph:6766-7380 /branches/INT64_BRANCH/bigdata/src/test/com/bigdata/bop/joinGraph:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/src/test/com/bigdata/bop/joinGraph:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/src/test/com/bigdata/bop/joinGraph:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/src/test/com/bigdata/bop/joinGraph:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/src/test/com/bigdata/bop/joinGraph:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/src/test/com/bigdata/bop/joinGraph:7465-7484 + /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/src/test/com/bigdata/bop/joinGraph:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/src/test/com/bigdata/bop/joinGraph:6766-7380 /branches/BIGDATA_RELEASE_1_3_0/bigdata/src/test/com/bigdata/bop/joinGraph:7608-7684 /branches/INT64_BRANCH/bigdata/src/test/com/bigdata/bop/joinGraph:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/src/test/com/bigdata/bop/joinGraph:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/src/test/com/bigdata/bop/joinGraph:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/src/test/com/bigdata/bop/joinGraph:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/src/test/com/bigdata/bop/joinGraph:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/src/test/com/bigdata/bop/joinGraph:7465-7484 Property changes on: branches/MGC_1_3_0/bigdata/src/test/com/bigdata/bop/util ___________________________________________________________________ Modified: svn:mergeinfo - /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/src/test/com/bigdata/bop/util:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/src/test/com/bigdata/bop/util:6766-7380 /branches/INT64_BRANCH/bigdata/src/test/com/bigdata/bop/util:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/src/test/com/bigdata/bop/util:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/src/test/com/bigdata/bop/util:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/src/test/com/bigdata/bop/util:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/src/test/com/bigdata/bop/util:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/src/test/com/bigdata/bop/util:7465-7484 + /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/src/test/com/bigdata/bop/util:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/src/test/com/bigdata/bop/util:6766-7380 /branches/BIGDATA_RELEASE_1_3_0/bigdata/src/test/com/bigdata/bop/util:7608-7684 /branches/INT64_BRANCH/bigdata/src/test/com/bigdata/bop/util:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/src/test/com/bigdata/bop/util:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/src/test/com/bigdata/bop/util:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/src/test/com/bigdata/bop/util:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/src/test/com/bigdata/bop/util:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/src/test/com/bigdata/bop/util:7465-7484 Modified: branches/MGC_1_3_0/bigdata/src/test/com/bigdata/io/TestNameAndExtensionFilter.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/test/com/bigdata/io/TestNameAndExtensionFilter.java 2013-12-19 21:11:18 UTC (rev 7684) +++ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/io/TestNameAndExtensionFilter.java 2013-12-19 21:34:30 UTC (rev 7685) @@ -53,7 +53,7 @@ /** * @param name */ - public TestNameAndExtensionFilter(String name) { + public TestNameAndExtensionFilter(final String name) { super(name); } @@ -64,85 +64,93 @@ * @param expected * @param actual */ - public void assertSameFiles( File[] expected, File[] actual ) - { - - if( expected == null ) { - - throw new AssertionError( "expected is null."); - + private void assertSameFiles(final File[] expected, final File[] actual) { + + if (expected == null) { + + throw new AssertionError("expected is null."); + } - if( actual == null ) { - - fail( "actual is null."); - + if (actual == null) { + + fail("actual is null."); + } - assertEquals( "#of files", expected.length, actual.length ); - + assertEquals("#of files", expected.length, actual.length); + // Insert the expected files into a set. - Set expectedSet = new HashSet(); - - for( int i=0; i<expected.length; i++ ) { + final Set<String> expectedSet = new HashSet<String>(); - File expectedFile = expected[ i ]; - - if( expectedFile == null ) { + for (int i = 0; i < expected.length; i++) { - throw new AssertionError( "expected file is null at index="+i ); - + final File expectedFile = expected[i]; + + if (expectedFile == null) { + + throw new AssertionError("expected file is null at index=" + i); + } - if( ! expectedSet.add( expectedFile.toString() ) ) { - - throw new AssertionError( "expected File[] contains duplicate: expected["+i+"]="+expectedFile ); - + if (!expectedSet.add(expectedFile.toString())) { + + throw new AssertionError( + "expected File[] contains duplicate: expected[" + i + + "]=" + expectedFile); + } - + } /* * Verify that each actual file occurs in the expectedSet using a * selection without replacement policy. */ - - for( int i=0; i<actual.length; i++ ) { - - File actualFile = actual[ i ]; - - if( actualFile == null ) { - - fail( "actual file is null at index="+i ); - + + for (int i = 0; i < actual.length; i++) { + + final File actualFile = actual[i]; + + if (actualFile == null) { + + fail("actual file is null at index=" + i); + } - - if( ! expectedSet.remove( actual[ i ].toString() ) ) { - - fail( "actual file="+actualFile+" at index="+i+" was not found in expected files." ); - + + if (!expectedSet.remove(actual[i].toString())) { + + fail("actual file=" + actualFile + " at index=" + i + + " was not found in expected files."); + } - + } - + } - + /** * Test verifies that no files are found using a guarenteed unique basename. */ - public void test_filter_001() throws IOException - { - - final File basefile = File.createTempFile(getName(),"-test"); - basefile.deleteOnExit(); - - final String basename = basefile.toString(); - System.err.println( "basename="+basename ); - - NameAndExtensionFilter logFilter = new NameAndExtensionFilter( basename, ".log" ); - - assertSameFiles( new File[]{}, logFilter.getFiles() ); - + public void test_filter_001() throws IOException { + + final File basefile = File.createTempFile(getName(), "-test"); + + try { + + final String basename = basefile.toString(); + + final NameAndExtensionFilter logFilter = new NameAndExtensionFilter( + basename, ".log"); + + assertSameFiles(new File[] {}, logFilter.getFiles()); + + } finally { + + basefile.delete(); + + } + } /** @@ -150,33 +158,48 @@ */ public void test_filter_002() throws IOException { - int N = 100; - - final File logBaseFile = File.createTempFile(getName(),"-test"); - logBaseFile.deleteOnExit(); - - final String basename = logBaseFile.toString(); - System.err.println( "basename="+basename ); - - NameAndExtensionFilter logFilter = new NameAndExtensionFilter( basename, ".log" ); + final int N = 100; - Vector v = new Vector( N ); - - for( int i=0; i<N; i++ ) { + final Vector<File> v = new Vector<File>(N); - File logFile = new File( basename+"."+i+".log" ); - logFile.deleteOnExit(); - logFile.createNewFile(); -// System.err.println( "logFile="+logFile ); - - v.add( logFile ); - + final File logBaseFile = File.createTempFile(getName(), "-test"); + // logBaseFile.deleteOnExit(); + + try { + + final String basename = logBaseFile.toString(); + // System.err.println( "basename="+basename ); + + final NameAndExtensionFilter logFilter = new NameAndExtensionFilter( + basename, ".log"); + + for (int i = 0; i < N; i++) { + + final File logFile = new File(basename + "." + i + ".log"); + // logFile.deleteOnExit(); + logFile.createNewFile(); + // System.err.println( "logFile="+logFile ); + + v.add(logFile); + + } + + final File[] expectedFiles = (File[]) v.toArray(new File[] {}); + + assertSameFiles(expectedFiles, logFilter.getFiles()); + + } finally { + + logBaseFile.delete(); + + for (File f : v) { + + f.delete(); + + } + } - File[] expectedFiles = (File[]) v.toArray(new File[]{}); - - assertSameFiles( expectedFiles, logFilter.getFiles() ); - } } Property changes on: branches/MGC_1_3_0/bigdata/src/test/com/bigdata/jsr166 ___________________________________________________________________ Modified: svn:mergeinfo - /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/src/test/com/bigdata/jsr166:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/src/test/com/bigdata/jsr166:6766-7380 /branches/INT64_BRANCH/bigdata/src/test/com/bigdata/jsr166:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/src/test/com/bigdata/jsr166:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/src/test/com/bigdata/jsr166:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/src/test/com/bigdata/jsr166:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/src/test/com/bigdata/jsr166:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/src/test/com/bigdata/jsr166:7465-7484 + /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/src/test/com/bigdata/jsr166:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/src/test/com/bigdata/jsr166:6766-7380 /branches/BIGDATA_RELEASE_1_3_0/bigdata/src/test/com/bigdata/jsr166:7608-7684 /branches/INT64_BRANCH/bigdata/src/test/com/bigdata/jsr166:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/src/test/com/bigdata/jsr166:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/src/test/com/bigdata/jsr166:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/src/test/com/bigdata/jsr166:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/src/test/com/bigdata/jsr166:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/src/test/com/bigdata/jsr166:7465-7484 Property changes on: branches/MGC_1_3_0/bigdata/src/test/com/bigdata/util/httpd ___________________________________________________________________ Modified: svn:mergeinfo - /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/src/test/com/bigdata/util/httpd:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/src/test/com/bigdata/util/httpd:6766-7380 /branches/INT64_BRANCH/bigdata/src/test/com/bigdata/util/httpd:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/src/test/com/bigdata/util/httpd:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/src/test/com/bigdata/util/httpd:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/src/test/com/bigdata/util/httpd:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/src/test/com/bigdata/util/httpd:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/src/test/com/bigdata/util/httpd:7465-7484 + /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/src/test/com/bigdata/util/httpd:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/src/test/com/bigdata/util/httpd:6766-7380 /branches/BIGDATA_RELEASE_1_3_0/bigdata/src/test/com/bigdata/util/httpd:7608-7684 /branches/INT64_BRANCH/bigdata/src/test/com/bigdata/util/httpd:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/src/test/com/bigdata/util/httpd:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/src/test/com/bigdata/util/httpd:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/src/test/com/bigdata/util/httpd:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/src/test/com/bigdata/util/httpd:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/src/test/com/bigdata/util/httpd:7465-7484 Property changes on: branches/MGC_1_3_0/bigdata-compatibility ___________________________________________________________________ Modified: svn:mergeinfo - /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata-compatibility:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata-compatibility:6766-7380 /branches/INT64_BRANCH/bigdata-compatibility:4486-4522 /branches/LARGE_LITERALS_REFACTOR/bigdata-compatibility:4175-4387 /branches/QUADS_QUERY_BRANCH/bigdata-compatibility:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata-compatibility:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata-compatibility:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata-compatibility:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata-compatibility:7465-7484 + /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata-compatibility:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata-compatibility:6766-7380 /branches/BIGDATA_RELEASE_1_3_0/bigdata-compatibility:7608-7684 /branches/INT64_BRANCH/bigdata-compatibility:4486-4522 /branches/LARGE_LITERALS_REFACTOR/bigdata-compatibility:4175-4387 /branches/QUADS_QUERY_BRANCH/bigdata-compatibility:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata-compatibility:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata-compatibility:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata-compatibility:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata-compatibility:7465-7484 Property changes on: branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/attr ___________________________________________________________________ Modified: svn:mergeinfo - /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata-jini/src/java/com/bigdata/attr:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata-jini/src/java/com/bigdata/attr:6766-7380 /branches/BTREE_BUFFER_BRANCH/bigdata-jini/src/java/com/bigdata/attr:2004-2045 /branches/DEV_BRANCH_27_OCT_2009/bigdata-jini/src/java/com/bigdata/attr:2270-2546,2548-2782 /branches/INT64_BRANCH/bigdata-jini/src/java/com/bigdata/attr:4486-4522 /branches/JOURNAL_HA_BRANCH/bigdata-jini/src/java/com/bigdata/attr:2596-4066 /branches/LARGE_LITERALS_REFACTOR/bigdata-jini/src/java/com/bigdata/attr:4175-4387 /branches/LEXICON_REFACTOR_BRANCH/bigdata-jini/src/java/com/bigdata/attr:2633-3304 /branches/QUADS_QUERY_BRANCH/bigdata-jini/src/java/com/bigdata/attr:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata-jini/src/java/com/bigdata/attr:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata-jini/src/java/com/bigdata/attr:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata-jini/src/java/com/bigdata/attr:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata-jini/src/java/com/bigdata/attr:7465-7484 /branches/bugfix-btm/bigdata-jini/src/java/com/bigdata/attr:2594-3237 /branches/dev-btm/bigdata-jini/src/java/com/bigdata/attr:2574-2730 /branches/fko/bigdata-jini/src/java/com/bigdata/attr:3150-3194 /trunk/bigdata-jini/src/java/com/bigdata/attr:2981-3282,3368-3437,3656-4061 + /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata-jini/src/java/com/bigdata/attr:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata-jini/src/java/com/bigdata/attr:6766-7380 /branches/BIGDATA_RELEASE_1_3_0/bigdata-jini/src/java/com/bigdata/attr:7608-7684 /branches/BTREE_BUFFER_BRANCH/bigdata-jini/src/java/com/bigdata/attr:2004-2045 /branches/DEV_BRANCH_27_OCT_2009/bigdata-jini/src/java/com/bigdata/attr:2270-2546,2548-2782 /branches/INT64_BRANCH/bigdata-jini/src/java/com/bigdata/attr:4486-4522 /branches/JOURNAL_HA_BRANCH/bigdata-jini/src/java/com/bigdata/attr:2596-4066 /branches/LARGE_LITERALS_REFACTOR/bigdata-jini/src/java/com/bigdata/attr:4175-4387 /branches/LEXICON_REFACTOR_BRANCH/bigdata-jini/src/java/com/bigdata/attr:2633-3304 /branches/QUADS_QUERY_BRANCH/bigdata-jini/src/java/com/bigdata/attr:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata-jini/src/java/com/bigdata/attr:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata-jini/src/java/com/bigdata/attr:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata-jini/src/java/com/bigdata/attr:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata-jini/src/java/com/bigdata/attr:7465-7484 /branches/bugfix-btm/bigdata-jini/src/java/com/bigdata/attr:2594-3237 /branches/dev-btm/bigdata-jini/src/java/com/bigdata/attr:2574-2730 /branches/fko/bigdata-jini/src/java/com/bigdata/attr:3150-3194 /trunk/bigdata-jini/src/java/com/bigdata/attr:2981-3282,3368-3437,3656-4061 Property changes on: branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/disco ___________________________________________________________________ Modified: svn:mergeinfo - /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata-jini/src/java/com/bigdata/disco:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata-jini/src/java/com/bigdata/disco:6766-7380 /branches/BTREE_BUFFER_BRANCH/bigdata-jini/src/java/com/bigdata/disco:2004-2045 /branches/DEV_BRANCH_27_OCT_2009/bigdata-jini/src/java/com/bigdata/disco:2270-2546,2548-2782 /branches/INT64_BRANCH/bigdata-jini/src/java/com/bigdata/disco:4486-4522 /branches/JOURNAL_HA_BRANCH/bigdata-jini/src/java/com/bigdata/disco:2596-4066 /branches/LARGE_LITERALS_REFACTOR/bigdata-jini/src/java/com/bigdata/disco:4175-4387 /branches/LEXICON_REFACTOR_BRANCH/bigdata-jini/src/java/com/bigdata/disco:2633-3304 /branches/QUADS_QUERY_BRANCH/bigdata-jini/src/java/com/bigdata/disco:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata-jini/src/java/com/bigdata/disco:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata-jini/src/java/com/bigdata/disco:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata-jini/src/java/com/bigdata/disco:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata-jini/src/java/com/bigdata/disco:7465-7484 /branches/bugfix-btm/bigdata-jini/src/java/com/bigdata/disco:2594-3237 /branches/dev-btm/bigdata-jini/src/java/com/bigdata/disco:2574-2730 /branches/fko/bigdata-jini/src/java/com/bigdata/disco:3150-3194 /trunk/bigdata-jini/src/java/com/bigdata/disco:2981-3282,3368-3437,3656-4061 + /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata-jini/src/java/com/bigdata/disco:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata-jini/src/java/com/bigdata/disco:6766-7380 /branches/BIGDATA_RELEASE_1_3_0/bigdata-jini/src/java/com/bigdata/disco:7608-7684 /branches/BTREE_BUFFER_BRANCH/bigdata-jini/src/java/com/bigdata/disco:2004-2045 /branches/DEV_BRANCH_27_OCT_2009/bigdata-jini/src/java/com/bigdata/disco:2270-2546,2548-2782 /branches/INT64_BRANCH/bigdata-jini/src/java/com/bigdata/disco:4486-4522 /branches/JOURNAL_HA_BRANCH/bigdata-jini/src/java/com/bigdata/disco:2596-4066 /branches/LARGE_LITERALS_REFACTOR/bigdata-jini/src/java/com/bigdata/disco:4175-4387 /branches/LEXICON_REFACTOR_BRANCH/bigdata-jini/src/java/com/bigdata/disco:2633-3304 /branches/QUADS_QUERY_BRANCH/bigdata-jini/src/java/com/bigdata/disco:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata-jini/src/java/com/bigdata/disco:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata-jini/src/java/com/bigdata/disco:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata-jini/src/java/com/bigdata/disco:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata-jini/src/java/com/bigdata/disco:7465-7484 /branches/bugfix-btm/bigdata-jini/src/java/com/bigdata/disco:2594-3237 /branches/dev-btm/bigdata-jini/src/java/com/bigdata/disco:2574-2730 /branches/fko/bigdata-jini/src/java/com/bigdata/disco:3150-3194 /trunk/bigdata-jini/src/java/com/bigdata/disco:2981-3282,3368-3437,3656-4061 Modified: branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/journal/jini/ha/DefaultSnapshotPolicy.java =================================================================== --- branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/journal/jini/ha/DefaultSnapshotPolicy.java 2013-12-19 21:11:18 UTC (rev 7684) +++ branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/journal/jini/ha/DefaultSnapshotPolicy.java 2013-12-19 21:34:30 UTC (rev 7685) @@ -136,6 +136,7 @@ } + @Override public void init(final HAJournal jnl) { // delay until next run (ms). Modified: branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/journal/jini/ha/HAJournal.java =================================================================== --- branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/journal/jini/ha/HAJournal.java 2013-12-19 21:11:18 UTC (rev 7684) +++ branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/journal/jini/ha/HAJournal.java 2013-12-19 21:34:30 UTC (rev 7685) @@ -54,6 +54,8 @@ import org.apache.log4j.Logger; import com.bigdata.concurrent.FutureTaskInvariantMon; +import com.bigdata.counters.CounterSet; +import com.bigdata.counters.Instrument; import com.bigdata.ha.HAGlue; import com.bigdata.ha.QuorumService; import com.bigdata.ha.RunState; @@ -94,6 +96,7 @@ import com.bigdata.journal.jini.ha.HAJournalServer.NSSConfigurationOptions; import com.bigdata.journal.jini.ha.HAJournalServer.RunStateEnum; import com.bigdata.quorum.Quorum; +import com.bigdata.resources.StoreManager.IStoreManagerCounters; import com.bigdata.service.AbstractTransactionService; import com.bigdata.service.jini.JiniClient; import com.bigdata.service.jini.RemoteAdministrable; @@ -729,6 +732,208 @@ // } /** + * Interface for additional performance counters exposed by the + * {@link HAJournal}. + * + * @author <a href="mailto:tho...@us...">Bryan + * Thompson</a> + */ + public interface IHAJournalCounters { + + /** + * The namespace for counters pertaining to free space on the various + * volumes. + */ + String Volumes = "Volumes"; + +// /** +// * The configured service directory. +// */ +// String ServiceDir = "ServiceDir"; +// +// /** +// * The configured data directory (the directory in which the Journal +// * file is stored). +// */ +// String DataDir = "DataDir"; +// +// /** +// * The configured HALog directory. +// */ +// String HALogDir = "HALogDir"; +// +// /** +// * The configured Snapshot directory. +// */ +// String SnapshotDir = "ShapshotDir"; +// +// /** +// * The configured tmp directory. +// */ +// String TmpDir = "TmpDir"; + + /** + * The #of bytes available on the disk volume on which the service + * directory is located. + * + * @see HAJournalServer#getServiceDir() + */ + String ServiceDirBytesAvailable = "Service Volume Bytes Available"; + + /** + * The #of bytes available on the disk volume on which the data + * directory is located (the directory in which the Journal file + * is stored). + * + * @see Journal#getDataDir() + */ + String DataDirBytesAvailable = "Data Volume Bytes Available"; + + /** + * The #of bytes available on the disk volume on which the HALog + * directory is located. + * + * @see HALogNexus#getHALogDir() + */ + String HALogDirBytesAvailable = "HALog Volume Bytes Available"; + + /** + * The #of bytes available on the disk volume on which the snapshot + * directory is located. + * + ... [truncated message content] |
From: <tho...@us...> - 2014-01-08 15:14:27
|
Revision: 7747 http://bigdata.svn.sourceforge.net/bigdata/?rev=7747&view=rev Author: thompsonbry Date: 2014-01-08 15:14:09 +0000 (Wed, 08 Jan 2014) Log Message: ----------- Merged in change set from the 1.3.0 maintenance and development branch in preparation for bringing this feature branch back to the main branch. At revision 7746. merge https://bigdata.svn.sourceforge.net/svnroot/bigdata/branches/BIGDATA_RELEASE_1_3_0 /Users/bryan/Documents/workspace/BIGDATA_RELEASE_1_3_0_MGC --- Merging r7684 through r7746 into /Users/bryan/Documents/workspace No conflicts. See #724 (HA wire pulling and sudden kills) Revision Links: -------------- http://bigdata.svn.sourceforge.net/bigdata/?rev=7746&view=rev http://bigdata.svn.sourceforge.net/bigdata/?rev=7684&view=rev http://bigdata.svn.sourceforge.net/bigdata/?rev=7746&view=rev Modified Paths: -------------- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/AbstractAccessPathOp.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/BOpBase.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/BOpContext.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/BOpIdFactory.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/BOpUtility.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/CoreBaseBOp.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/IdFactory.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/ap/SampleIndex.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/constraint/Constraint.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/controller/HTreeNamedSubqueryOp.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/controller/JVMNamedSubqueryOp.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/controller/ServiceCallJoin.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/engine/AbstractRunningQuery.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/engine/BOpStats.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/engine/ChunkedRunningQuery.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/engine/LocalChunkMessage.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/engine/QueryEngine.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/engine/QueryLog.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/engine/RunState.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/fed/EmptyChunkMessage.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/fed/NIOChunkMessage.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/fed/ThickChunkMessage.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/join/BaseJoinStats.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/join/HTreeHashIndexOp.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/join/HTreeHashJoinUtility.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/join/HashIndexOp.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/join/HashJoinOp.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/join/IHashJoinUtility.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/join/JVMHashIndex.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/join/JVMHashIndexOp.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/join/JVMHashJoinUtility.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/join/JoinVariableNotBoundException.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/join/NamedSolutionSetStats.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/join/PipelineJoin.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/join/PipelineJoinStats.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/join/SolutionSetHashJoinOp.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/joinGraph/PartitionedJoinGroup.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/joinGraph/rto/JGraph.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/joinGraph/rto/JoinGraph.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/joinGraph/rto/Path.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/joinGraph/rto/PathIds.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/joinGraph/rto/SampleBase.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/joinGraph/rto/Vertex.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/paths/ZeroLengthPathOp.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/solutions/DropOp.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/solutions/GroupByOp.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/solutions/GroupByRewriter.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/solutions/GroupByState.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/solutions/MemoryGroupByOp.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/solutions/PipelinedAggregationOp.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/solutions/ProjectionOp.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/solutions/SliceOp.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/btree/data/DefaultLeafCoder.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/btree/data/DefaultNodeCoder.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/journal/Options.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/relation/accesspath/AccessPath.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/relation/accesspath/IBindingSetAccessPath.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/relation/accesspath/MultiSourceSequentialCloseableIterator.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/striterator/AbstractChunkedResolverator.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/striterator/ChunkedArrayIterator.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/striterator/ChunkedArraysIterator.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/striterator/ChunkedConvertingIterator.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/striterator/ChunkedOrderedStriterator.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/striterator/ChunkedResolvingIterator.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/striterator/ChunkedWrappedIterator.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/striterator/Chunkerator.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/striterator/CloseableIteratorWrapper.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/striterator/Dechunkerator.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/striterator/DelegateChunkedIterator.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/striterator/GenericChunkedStriterator.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/striterator/IChunkedIterator.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/striterator/IChunkedStriterator.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/striterator/MergeFilter.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/striterator/PushbackIterator.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/striterator/Resolver.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/striterator/Striterator.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/util/NT.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/bop/TestAll.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/bop/fed/TestNIOChunkMessage.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/bop/join/AbstractHashJoinUtilityTestCase.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/bop/join/TestPipelineJoin.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/bop/joinGraph/rto/TestAll.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/bop/joinGraph/rto/TestJGraph.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/bop/joinGraph/rto/TestJoinGraph.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/striterator/TestAll.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/bop/rdf/join/ChunkedMaterializationOp.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/bop/rdf/update/ParserStats.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/inf/BackchainTypeResourceIterator.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/internal/constraints/IPassesMaterialization.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/internal/constraints/SPARQLConstraint.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/ASTBase.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/AssignmentNode.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/GraphPatternGroup.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/GroupNodeBase.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/JoinGroupNode.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/NamedSubqueryInclude.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/OrderByNode.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/QueryBase.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/QueryHints.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/QueryOptimizerEnum.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/QueryRoot.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/SliceNode.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/StatementPatternNode.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/ValueExpressionListBaseNode.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/ZeroLengthPathNode.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/eval/AST2BOpBase.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/eval/AST2BOpContext.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/eval/AST2BOpFilters.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/eval/AST2BOpJoins.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/eval/AST2BOpUtility.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/eval/SliceServiceFactory.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/hints/AbstractChunkSizeHint.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/hints/AbstractQueryHint.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/hints/AnalyticQueryHint.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/hints/AtOnceHint.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/hints/BufferChunkCapacityHint.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/hints/BufferChunkOfChunksCapacityHint.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/hints/ChunkSizeHint.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/hints/IQueryHint.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/hints/OptimizerQueryHint.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/hints/PipelineMaxMessagesPerTaskHint.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/hints/PipelineMaxParallelHint.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/hints/PipelineQueueCapacityHint.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/hints/QueryHintRegistry.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/optimizers/ASTBindingAssigner.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/optimizers/ASTBottomUpOptimizer.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/optimizers/ASTJoinOrderByTypeOptimizer.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/optimizers/ASTQueryHintOptimizer.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/optimizers/ASTRangeCountOptimizer.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/optimizers/ASTSparql11SubqueryOptimizer.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/optimizers/ASTStaticJoinOptimizer.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/service/ServiceCall.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/store/BDS.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/store/DataLoader.java branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/AbstractDataAndSPARQLTestCase.java branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/AbstractDataDrivenSPARQLTestCase.java branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/TestQueryHints.java branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/query-hints-01.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/query-hints-06.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/optimizers/AbstractOptimizerTestCase.java branches/MGC_1_3_0/bigdata-sails/src/java/com/bigdata/rdf/sail/webapp/BigdataRDFContext.java branches/MGC_1_3_0/bigdata-sails/src/java/com/bigdata/rdf/sail/webapp/QueryServlet.java branches/MGC_1_3_0/bigdata-sails/src/java/com/bigdata/rdf/sail/webapp/StatusServlet.java branches/MGC_1_3_0/bigdata-sails/src/test/com/bigdata/rdf/sail/webapp/AbstractProtocolTest.java branches/MGC_1_3_0/bigdata-sails/src/test/com/bigdata/rdf/sail/webapp/TestNanoSparqlServerWithProxyIndexManager.java branches/MGC_1_3_0/bigdata-war/src/html/index.html Added Paths: ----------- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/SimpleIdFactory.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/controller/INamedSubqueryOp.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/striterator/CloseableChunkedIteratorWrapperConverter.java branches/MGC_1_3_0/bigdata/src/resources/deployment/ branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/ branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/ branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/Berksfile branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/CHANGELOG.md branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/Gemfile branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/README.md branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/Thorfile branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/Vagrantfile branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/attributes/ branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/attributes/default.rb branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/chefignore branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/files/ branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/files/default/ branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/files/default/test/ branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/files/default/test/default_test.rb branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/metadata.rb branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/recipes/ branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/recipes/default.rb branches/MGC_1_3_0/bigdata/src/test/com/bigdata/striterator/TestCloseableChunkedIteratorWrapperConverter.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/eval/AST2BOpRTO.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/hints/RTOLimitQueryHint.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/hints/RTONEdgesQueryHint.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/hints/RTOSampleTypeQueryHint.java branches/MGC_1_3_0/bigdata-rdf/src/resources/data/lehigh/LUBM-U1.rdf.gz branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/ branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/AbstractRTOTestCase.java branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BAR-Q1.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BAR-Q1.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q1.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q1.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q10.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q10.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q2.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q2.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q3.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q3.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q4.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q4.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q5.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q5.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q7.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q7.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q8.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q8.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/LUBM-Q2.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/LUBM-Q2.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/LUBM-Q8.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/LUBM-Q8.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/LUBM-Q9.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/LUBM-Q9.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/TestAll.java branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/TestRTO_BAR.java branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/TestRTO_BSBM.java branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/TestRTO_LUBM.java branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/optimizers/TestASTMassagedServiceNodeOptimizer.java branches/MGC_1_3_0/bigdata-sails/src/test/com/bigdata/rdf/sail/webapp/TestService794.java Removed Paths: ------------- branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/ branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/ branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/Berksfile branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/CHANGELOG.md branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/Gemfile branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/README.md branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/Thorfile branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/Vagrantfile branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/attributes/ branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/attributes/default.rb branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/chefignore branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/files/ branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/files/default/ branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/files/default/test/ branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/files/default/test/default_test.rb branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/metadata.rb branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/recipes/ branches/MGC_1_3_0/bigdata/src/resources/deployment/vagrant/systap-bigdata/recipes/default.rb branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/AbstractRTOTestCase.java branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BAR-Q1.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BAR-Q1.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q1.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q1.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q10.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q10.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q2.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q2.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q3.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q3.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q4.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q4.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q5.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q5.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q7.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q7.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q8.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/BSBM-Q8.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/LUBM-Q2.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/LUBM-Q2.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/LUBM-Q8.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/LUBM-Q8.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/LUBM-Q9.rq branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/LUBM-Q9.srx branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/TestAll.java branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/TestRTO_BAR.java branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/TestRTO_BSBM.java branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/sparql/ast/eval/rto/TestRTO_LUBM.java Property Changed: ---------------- branches/MGC_1_3_0/ branches/MGC_1_3_0/bigdata/lib/jetty/ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/aggregate/ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/joinGraph/ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/util/ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/htree/raba/ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/jsr166/ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/bop/joinGraph/ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/bop/util/ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/jsr166/ branches/MGC_1_3_0/bigdata/src/test/com/bigdata/util/httpd/ branches/MGC_1_3_0/bigdata-compatibility/ branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/attr/ branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/disco/ branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/util/config/ branches/MGC_1_3_0/bigdata-perf/ branches/MGC_1_3_0/bigdata-perf/btc/ branches/MGC_1_3_0/bigdata-perf/btc/src/resources/ branches/MGC_1_3_0/bigdata-perf/lubm/ branches/MGC_1_3_0/bigdata-perf/uniprot/ branches/MGC_1_3_0/bigdata-perf/uniprot/src/ branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/bop/rdf/aggregate/ branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/changesets/ branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/error/ branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/internal/ branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/relation/ branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/util/ branches/MGC_1_3_0/bigdata-rdf/src/samples/ branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/bop/rdf/aggregate/ branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/internal/ branches/MGC_1_3_0/bigdata-rdf/src/test/com/bigdata/rdf/relation/ branches/MGC_1_3_0/bigdata-sails/src/java/com/bigdata/rdf/sail/bench/ branches/MGC_1_3_0/bigdata-sails/src/java/com/bigdata/rdf/sail/changesets/ branches/MGC_1_3_0/bigdata-sails/src/java/com/bigdata/rdf/sail/webapp/ branches/MGC_1_3_0/bigdata-sails/src/test/com/bigdata/rdf/sail/bench/ branches/MGC_1_3_0/bigdata-sails/src/test/com/bigdata/rdf/sail/webapp/ branches/MGC_1_3_0/dsi-utils/ branches/MGC_1_3_0/dsi-utils/LEGAL/ branches/MGC_1_3_0/dsi-utils/lib/ branches/MGC_1_3_0/dsi-utils/src/ branches/MGC_1_3_0/dsi-utils/src/java/ branches/MGC_1_3_0/dsi-utils/src/java/it/ branches/MGC_1_3_0/dsi-utils/src/java/it/unimi/ branches/MGC_1_3_0/dsi-utils/src/test/ branches/MGC_1_3_0/dsi-utils/src/test/it/unimi/ branches/MGC_1_3_0/dsi-utils/src/test/it/unimi/dsi/ branches/MGC_1_3_0/lgpl-utils/src/java/it/unimi/dsi/fastutil/bytes/custom/ branches/MGC_1_3_0/lgpl-utils/src/test/it/unimi/dsi/fastutil/bytes/custom/ branches/MGC_1_3_0/osgi/ branches/MGC_1_3_0/src/resources/bin/config/ Property changes on: branches/MGC_1_3_0 ___________________________________________________________________ Modified: svn:ignore - ant-build src bin bigdata*.jar ant-release standalone test* countersfinal.xml events.jnl .settings *.jnl TestInsertRate.out SYSTAP-BBT-result.txt U10load+query *.hprof com.bigdata.cache.TestHardReferenceQueueWithBatchingUpdates.exp.csv commit-log.txt eventLog dist bigdata-test com.bigdata.rdf.stress.LoadClosureAndQueryTest.*.csv DIST.bigdata-*.tgz REL.bigdata-*.tgz queryLog* queryRunState* sparql.txt benchmark CI + ant-build src bin bigdata*.jar ant-release standalone test* countersfinal.xml events.jnl .settings *.jnl TestInsertRate.out SYSTAP-BBT-result.txt U10load+query *.hprof com.bigdata.cache.TestHardReferenceQueueWithBatchingUpdates.exp.csv commit-log.txt eventLog dist bigdata-test com.bigdata.rdf.stress.LoadClosureAndQueryTest.*.csv DIST.bigdata-*.tgz REL.bigdata-*.tgz queryLog* queryRunState* sparql.txt benchmark CI bsbm10-dataset.nt.gz bsbm10-dataset.nt.zip Modified: svn:mergeinfo - /branches/BIGDATA_OPENRDF_2_6_9_UPDATE:6769-6785 /branches/BIGDATA_RELEASE_1_2_0:6766-7380 /branches/BIGDATA_RELEASE_1_3_0:7608-7684 /branches/BTREE_BUFFER_BRANCH:2004-2045 /branches/DEV_BRANCH_27_OCT_2009:2270-2546,2548-2782 /branches/INT64_BRANCH:4486-4522 /branches/JOURNAL_HA_BRANCH:2596-4066 /branches/LARGE_LITERALS_REFACTOR:4175-4387 /branches/LEXICON_REFACTOR_BRANCH:2633-3304 /branches/QUADS_QUERY_BRANCH:4525-4531,4550-4584,4586-4609,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE:7215-7271 /branches/RWSTORE_1_1_0_DEBUG:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH:4814-4836 /branches/ZK_DISCONNECT_HANDLING:7465-7484 /branches/bugfix-btm:2594-3237 /branches/dev-btm:2574-2730 /branches/fko:3150-3194 /trunk:3392-3437,3656-4061 + /branches/BIGDATA_OPENRDF_2_6_9_UPDATE:6769-6785 /branches/BIGDATA_RELEASE_1_2_0:6766-7380 /branches/BIGDATA_RELEASE_1_3_0:7608-7746 /branches/BTREE_BUFFER_BRANCH:2004-2045 /branches/DEV_BRANCH_27_OCT_2009:2270-2546,2548-2782 /branches/INT64_BRANCH:4486-4522 /branches/JOURNAL_HA_BRANCH:2596-4066 /branches/LARGE_LITERALS_REFACTOR:4175-4387 /branches/LEXICON_REFACTOR_BRANCH:2633-3304 /branches/QUADS_QUERY_BRANCH:4525-4531,4550-4584,4586-4609,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE:7215-7271 /branches/RWSTORE_1_1_0_DEBUG:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH:4814-4836 /branches/ZK_DISCONNECT_HANDLING:7465-7484 /branches/bugfix-btm:2594-3237 /branches/dev-btm:2574-2730 /branches/fko:3150-3194 /trunk:3392-3437,3656-4061 Property changes on: branches/MGC_1_3_0/bigdata/lib/jetty ___________________________________________________________________ Modified: svn:mergeinfo - /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/lib/jetty:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/lib/jetty:6766-7380 /branches/BIGDATA_RELEASE_1_3_0/bigdata/lib/jetty:7608-7684 /branches/INT64_BRANCH/bigdata/lib/jetty:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/lib/jetty:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/lib/jetty:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/lib/jetty:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/lib/jetty:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/lib/jetty:7465-7484 + /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/lib/jetty:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/lib/jetty:6766-7380 /branches/BIGDATA_RELEASE_1_3_0/bigdata/lib/jetty:7608-7746 /branches/INT64_BRANCH/bigdata/lib/jetty:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/lib/jetty:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/lib/jetty:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/lib/jetty:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/lib/jetty:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/lib/jetty:7465-7484 Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/AbstractAccessPathOp.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/AbstractAccessPathOp.java 2014-01-07 22:10:34 UTC (rev 7746) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/AbstractAccessPathOp.java 2014-01-08 15:14:09 UTC (rev 7747) @@ -76,26 +76,26 @@ super(op); } - /** - * @see BufferAnnotations#CHUNK_CAPACITY - */ - protected int getChunkCapacity() { - - return getProperty(Annotations.CHUNK_CAPACITY, - Annotations.DEFAULT_CHUNK_CAPACITY); +// /** +// * @see BufferAnnotations#CHUNK_CAPACITY +// */ +// protected int getChunkCapacity() { +// +// return getProperty(Annotations.CHUNK_CAPACITY, +// Annotations.DEFAULT_CHUNK_CAPACITY); +// +// } +// +// /** +// * @see BufferAnnotations#CHUNK_OF_CHUNKS_CAPACITY +// */ +// protected int getChunkOfChunksCapacity() { +// +// return getProperty(Annotations.CHUNK_OF_CHUNKS_CAPACITY, +// Annotations.DEFAULT_CHUNK_OF_CHUNKS_CAPACITY); +// +// } - } - - /** - * @see BufferAnnotations#CHUNK_OF_CHUNKS_CAPACITY - */ - protected int getChunkOfChunksCapacity() { - - return getProperty(Annotations.CHUNK_OF_CHUNKS_CAPACITY, - Annotations.DEFAULT_CHUNK_OF_CHUNKS_CAPACITY); - - } - // protected int getFullyBufferedReadThreshold() { // // return getProperty(Annotations.FULLY_BUFFERED_READ_THRESHOLD, @@ -103,14 +103,14 @@ // // } - /** - * @see BufferAnnotations#CHUNK_TIMEOUT - */ - protected long getChunkTimeout() { - - return getProperty(Annotations.CHUNK_TIMEOUT, - Annotations.DEFAULT_CHUNK_TIMEOUT); - - } +// /** +// * @see BufferAnnotations#CHUNK_TIMEOUT +// */ +// protected long getChunkTimeout() { +// +// return getProperty(Annotations.CHUNK_TIMEOUT, +// Annotations.DEFAULT_CHUNK_TIMEOUT); +// +// } } Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/BOpBase.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/BOpBase.java 2014-01-07 22:10:34 UTC (rev 7746) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/BOpBase.java 2014-01-08 15:14:09 UTC (rev 7747) @@ -175,6 +175,7 @@ } + @Override final public Map<String, Object> annotations() { return Collections.unmodifiableMap(annotations); @@ -234,6 +235,7 @@ } + @Override public BOp get(final int index) { return args[index]; @@ -286,6 +288,7 @@ } + @Override public int arity() { return args.length; @@ -297,6 +300,7 @@ * <p> * Note: This is much less efficient than {@link #argIterator()}. */ + @Override final public List<BOp> args() { return Collections.unmodifiableList(Arrays.asList(args)); @@ -309,6 +313,7 @@ * The iterator does not support removal. (This is more efficient than * #args()). */ + @Override final public Iterator<BOp> argIterator() { return new ArgIterator(); @@ -339,6 +344,7 @@ } // shallow copy + @Override public BOp[] toArray() { final BOp[] a = new BOp[args.length]; @@ -475,6 +481,7 @@ // // } + @Override public Object getProperty(final String name) { return annotations.get(name); @@ -543,6 +550,7 @@ } + @Override public BOpBase setProperty(final String name, final Object value) { final BOpBase tmp = (BOpBase) this.clone(); Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/BOpContext.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/BOpContext.java 2014-01-07 22:10:34 UTC (rev 7746) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/BOpContext.java 2014-01-08 15:14:09 UTC (rev 7747) @@ -59,8 +59,9 @@ import com.bigdata.rwstore.sector.IMemoryManager; import com.bigdata.striterator.ChunkedFilter; import com.bigdata.striterator.Chunkerator; -import com.bigdata.striterator.CloseableIteratorWrapper; +import com.bigdata.striterator.CloseableChunkedIteratorWrapperConverter; import com.bigdata.striterator.IChunkedIterator; +import com.bigdata.striterator.IChunkedStriterator; import cutthecrap.utils.striterators.ICloseableIterator; @@ -1078,8 +1079,8 @@ } /** - * Convert an {@link IAccessPath#iterator()} into a stream of - * {@link IBindingSet}s. + * Convert an {@link IAccessPath#iterator()} into a stream of chunks of + * {@link IBindingSet}. * * @param src * The iterator draining the {@link IAccessPath}. This will visit @@ -1090,7 +1091,7 @@ * Statistics to be updated as elements and chunks are consumed * (optional). * - * @return The dechunked iterator visiting the solutions. The order of the + * @return An iterator visiting chunks of solutions. The order of the * original {@link IElement}s is preserved. * * @see https://sourceforge.net/apps/trac/bigdata/ticket/209 (AccessPath @@ -1105,14 +1106,15 @@ // * The array of distinct variables (no duplicates) to be // * extracted from the visited {@link IElement}s. @SuppressWarnings({ "rawtypes", "unchecked" }) - static public ICloseableIterator<IBindingSet> solutions( + static public ICloseableIterator<IBindingSet[]> solutions( final IChunkedIterator<?> src, // final IPredicate<?> pred,// // final IVariable<?>[] varsx, final BaseJoinStats stats// ) { - return new CloseableIteratorWrapper( + //return new CloseableIteratorWrapper( + final IChunkedStriterator itr1 = new com.bigdata.striterator.ChunkedStriterator(src).addFilter( // new ChunkedFilter() { new ChunkedFilter<IChunkedIterator<Object>, Object, Object>() { @@ -1160,18 +1162,28 @@ } - })) { + }); + //) { +// +// /** +// * Close the real source if the caller closes the returned iterator. +// */ +// @Override +// public void close() { +// super.close(); +// src.close(); +// } +// }; - /** - * Close the real source if the caller closes the returned iterator. - */ - @Override - public void close() { - super.close(); - src.close(); - } - }; + /* + * Convert from IChunkedIterator<IBindingSet> to + * ICloseableIterator<IBindingSet[]>. This is a fly weight conversion. + */ + final ICloseableIterator<IBindingSet[]> itr2 = new CloseableChunkedIteratorWrapperConverter<IBindingSet>( + itr1); + return itr2; + } /* Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/BOpIdFactory.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/BOpIdFactory.java 2014-01-07 22:10:34 UTC (rev 7746) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/BOpIdFactory.java 2014-01-08 15:14:09 UTC (rev 7747) @@ -1,5 +1,29 @@ +/** + +Copyright (C) SYSTAP, LLC 2006-2011. All rights reserved. + +Contact: + SYSTAP, LLC + 4501 Tower Road + Greensboro, NC 27410 + lic...@bi... + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; version 2 of the License. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ package com.bigdata.bop; +import java.util.Iterator; import java.util.LinkedHashSet; /** @@ -7,23 +31,102 @@ */ public class BOpIdFactory implements IdFactory { - private final LinkedHashSet<Integer> ids = new LinkedHashSet<Integer>(); - - private int nextId = 0; - - public void reserve(int id) { - ids.add(id); - } + /** The set of reserved bop identifiers. */ + private LinkedHashSet<Integer> ids; - public int nextId() { + private int nextId = 0; - while (ids.contains(nextId)) { + /** + * Reserve a bop id by adding it to a set of known identifiers that will not + * be issued by {@link #nextId()}. + * + * @param id + * The identifier. + */ + public void reserve(final int id) { + + synchronized (this) { + + if (ids == null) { - nextId++; - - } + // Lazily allocated. + ids = new LinkedHashSet<Integer>(); - return nextId++; - } - + ids.add(id); + + } + + } + + } + + @Override + public int nextId() { + + synchronized (this) { + + if (ids != null) { + + while (ids.contains(nextId)) { + + nextId++; + + } + + } + + return nextId++; + + } + + } + + /** + * Reserve ids used by the predicates or constraints associated with some + * join graph. + * + * @param preds + * The vertices of the join graph. + * @param constraints + * The constraints of the join graph (optional). + */ + public void reserveIds(final IPredicate<?>[] preds, + final IConstraint[] constraints) { + + if (preds == null) + throw new IllegalArgumentException(); + + final BOpIdFactory idFactory = this; + + for (IPredicate<?> p : preds) { + + idFactory.reserve(p.getId()); + + } + + if (constraints != null) { + + for (IConstraint c : constraints) { + + final Iterator<BOp> itr = BOpUtility + .preOrderIteratorWithAnnotations(c); + + while (itr.hasNext()) { + + final BOp y = itr.next(); + + final Integer anId = (Integer) y + .getProperty(BOp.Annotations.BOP_ID); + + if (anId != null) + idFactory.reserve(anId.intValue()); + + } + + } + + } + + } + } \ No newline at end of file Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/BOpUtility.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/BOpUtility.java 2014-01-07 22:10:34 UTC (rev 7746) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/BOpUtility.java 2014-01-08 15:14:09 UTC (rev 7747) @@ -35,6 +35,7 @@ import java.util.LinkedList; import java.util.List; import java.util.Map; +import java.util.NoSuchElementException; import java.util.Set; import org.apache.log4j.Logger; @@ -53,6 +54,7 @@ import cutthecrap.utils.striterators.EmptyIterator; import cutthecrap.utils.striterators.Expander; import cutthecrap.utils.striterators.Filter; +import cutthecrap.utils.striterators.ICloseable; import cutthecrap.utils.striterators.ICloseableIterator; import cutthecrap.utils.striterators.SingleValueIterator; import cutthecrap.utils.striterators.Striterator; @@ -72,7 +74,7 @@ * Pre-order recursive visitation of the operator tree (arguments only, no * annotations). */ - @SuppressWarnings("unchecked") + @SuppressWarnings({ "unchecked", "rawtypes" }) public static Iterator<BOp> preOrderIterator(final BOp op) { return new Striterator(new SingleValueIterator(op)) @@ -466,6 +468,8 @@ * The type of the node to be extracted. * * @return A list containing those references. + * + * @see #visitAll(BOp, Class) */ public static <C> List<C> toList(final BOp op, final Class<C> clas) { @@ -483,6 +487,44 @@ } + /** + * Return the sole instance of the specified class. + * + * @param op + * The root of the traversal. + * @param class1 + * The class to look for. + * @return The sole instance of that class. + * @throws NoSuchElementException + * if there is no such instance. + * @throws RuntimeException + * if there is more than one such instance. + */ + public static <C> C getOnly(final BOp op, final Class<C> class1) { + final Iterator<C> it = visitAll(op, class1); + if (!it.hasNext()) + throw new NoSuchElementException("No instance found: class=" + + class1); + final C ret = it.next(); + if (it.hasNext()) + throw new RuntimeException("More than one instance exists: class=" + + class1); + return ret; + } + + /** + * Return an iterator visiting references to all nodes of the given type + * (recursive, including annotations). + * + * @param op + * The root of the operator tree. + * @param clas + * The type of the node to be extracted. + * + * @return A iterator visiting those references. + * + * @see #toList(BOp, Class) + */ @SuppressWarnings("unchecked") public static <C> Iterator<C> visitAll(final BOp op, final Class<C> clas) { @@ -947,9 +989,9 @@ } finally { - if (itr instanceof ICloseableIterator<?>) { + if (itr instanceof ICloseable) { - ((ICloseableIterator<?>) itr).close(); + ((ICloseable) itr).close(); } Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/CoreBaseBOp.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/CoreBaseBOp.java 2014-01-07 22:10:34 UTC (rev 7746) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/CoreBaseBOp.java 2014-01-08 15:14:09 UTC (rev 7747) @@ -75,6 +75,7 @@ * <p> * {@inheritDoc} */ + @Override public CoreBaseBOp clone() { final Class<? extends CoreBaseBOp> cls = getClass(); final Constructor<? extends CoreBaseBOp> ctor; @@ -98,14 +99,15 @@ * General contract is a short (non-recursive) representation of the * {@link BOp}. */ + @Override public String toShortString() { final BOp t = this; if (t instanceof IValueExpression<?> || t instanceof IValueExpressionNode) { /* - * Note: toString() is intercepted for a few bops, mainly those with - * a pretty simple structure. This delegates to toString() in those - * cases. + * Note: toShortString() is intercepted for a few bops, mainly those + * with a pretty simple structure. This delegates to toString() in + * those cases. */ return t.toString(); } else { @@ -125,6 +127,7 @@ * Return a non-recursive representation of the arguments and annotations * for this {@link BOp}. */ + @Override public String toString() { final StringBuilder sb = new StringBuilder(); @@ -181,6 +184,7 @@ } } + @Override final public Object getRequiredProperty(final String name) { final Object tmp = getProperty(name); @@ -193,6 +197,7 @@ } + @Override @SuppressWarnings("unchecked") final public <T> T getProperty(final String name, final T defaultValue) { @@ -229,18 +234,22 @@ } + @Override final public int getId() { return (Integer) getRequiredProperty(Annotations.BOP_ID); } - + + @Override final public boolean isController() { - - return getProperty(Annotations.CONTROLLER, false); - + + return getProperty(Annotations.CONTROLLER, + Annotations.DEFAULT_CONTROLLER); + } + @Override final public BOpEvaluationContext getEvaluationContext() { return getProperty(Annotations.EVALUATION_CONTEXT, @@ -251,6 +260,7 @@ /** * <code>true</code> if all arguments and annotations are the same. */ + @Override public boolean equals(final Object other) { if (this == other) @@ -378,6 +388,7 @@ /** * The hash code is based on the hash of the operands (cached). */ + @Override public int hashCode() { int h = hash; Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/IdFactory.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/IdFactory.java 2014-01-07 22:10:34 UTC (rev 7746) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/IdFactory.java 2014-01-08 15:14:09 UTC (rev 7747) @@ -1,3 +1,26 @@ +/** + +Copyright (C) SYSTAP, LLC 2006-2011. All rights reserved. + +Contact: + SYSTAP, LLC + 4501 Tower Road + Greensboro, NC 27410 + lic...@bi... + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; version 2 of the License. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ package com.bigdata.bop; /** @@ -5,6 +28,9 @@ */ public interface IdFactory { + /** + * Issue the next bop identifier. + */ public int nextId(); } Copied: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/SimpleIdFactory.java (from rev 7746, branches/BIGDATA_RELEASE_1_3_0/bigdata/src/java/com/bigdata/bop/SimpleIdFactory.java) =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/SimpleIdFactory.java (rev 0) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/SimpleIdFactory.java 2014-01-08 15:14:09 UTC (rev 7747) @@ -0,0 +1,47 @@ +/** + +Copyright (C) SYSTAP, LLC 2006-2011. All rights reserved. + +Contact: + SYSTAP, LLC + 4501 Tower Road + Greensboro, NC 27410 + lic...@bi... + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; version 2 of the License. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ +package com.bigdata.bop; + +import java.util.concurrent.atomic.AtomicInteger; + +public class SimpleIdFactory implements IdFactory { + + /** + * Note: The ids are assigned using {@link AtomicInteger#incrementAndGet()} + * so ONE (1) is the first id that will be assigned when we pass in ZERO (0) + * as the initial state of the {@link AtomicInteger}. + */ + private final AtomicInteger nextId = new AtomicInteger(0); + + /** + * {@inheritDoc} + */ + @Override + public int nextId() { + + return nextId.incrementAndGet(); + + } + +} Property changes on: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/aggregate ___________________________________________________________________ Modified: svn:mergeinfo - /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/src/java/com/bigdata/bop/aggregate:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/src/java/com/bigdata/bop/aggregate:6766-7380 /branches/BIGDATA_RELEASE_1_3_0/bigdata/src/java/com/bigdata/bop/aggregate:7608-7684 /branches/INT64_BRANCH/bigdata/src/java/com/bigdata/bop/aggregate:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/src/java/com/bigdata/bop/aggregate:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/src/java/com/bigdata/bop/aggregate:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/src/java/com/bigdata/bop/aggregate:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/src/java/com/bigdata/bop/aggregate:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/src/java/com/bigdata/bop/aggregate:7465-7484 + /branches/BIGDATA_OPENRDF_2_6_9_UPDATE/bigdata/src/java/com/bigdata/bop/aggregate:6769-6785 /branches/BIGDATA_RELEASE_1_2_0/bigdata/src/java/com/bigdata/bop/aggregate:6766-7380 /branches/BIGDATA_RELEASE_1_3_0/bigdata/src/java/com/bigdata/bop/aggregate:7608-7746 /branches/INT64_BRANCH/bigdata/src/java/com/bigdata/bop/aggregate:4486-4522 /branches/QUADS_QUERY_BRANCH/bigdata/src/java/com/bigdata/bop/aggregate:4525-4531,4533-4548,4550-4584,4586-4609,4611-4632,4634-4643,4646-4672,4674-4685,4687-4693,4697-4735,4737-4782,4784-4792,4794-4796,4798-4801 /branches/READ_CACHE/bigdata/src/java/com/bigdata/bop/aggregate:7215-7271 /branches/RWSTORE_1_1_0_DEBUG/bigdata/src/java/com/bigdata/bop/aggregate:5896-5935 /branches/TIDS_PLUS_BLOBS_BRANCH/bigdata/src/java/com/bigdata/bop/aggregate:4814-4836 /branches/ZK_DISCONNECT_HANDLING/bigdata/src/java/com/bigdata/bop/aggregate:7465-7484 Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/ap/SampleIndex.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/ap/SampleIndex.java 2014-01-07 22:10:34 UTC (rev 7746) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/ap/SampleIndex.java 2014-01-08 15:14:09 UTC (rev 7747) @@ -106,7 +106,13 @@ /** * Sample offsets are computed randomly. */ - RANDOM; + RANDOM, + /** + * The samples will be dense and may bave a front bias. This mode + * emphasizes the locality of the samples on the index pages and + * minimizes the IO associated with sampling. + */ + DENSE; } /** @@ -323,6 +329,9 @@ seed(), limit, accessPath.getFromKey(), accessPath .getToKey()); break; + case DENSE: + advancer = new DenseSampleAdvancer<E>(); + break; default: throw new UnsupportedOperationException("SampleType=" + sampleType); @@ -339,6 +348,23 @@ } /** + * Dense samples in key order (simple index scan). + * + * @author <a href="mailto:tho...@us...">Bryan Thompson</a> + * @param <E> + */ + private static class DenseSampleAdvancer<E> extends Advancer<E> { + + private static final long serialVersionUID = 1L; + + @Override + protected void advance(final ITuple<E> tuple) { + // NOP + } + + } + + /** * An advancer pattern which is designed to take evenly distributed samples * from an index. The caller specifies the #of tuples to be sampled. This * class estimates the range count of the access path and then computes the Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/constraint/Constraint.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/constraint/Constraint.java 2014-01-07 22:10:34 UTC (rev 7746) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/constraint/Constraint.java 2014-01-08 15:14:09 UTC (rev 7747) @@ -34,7 +34,7 @@ import com.bigdata.bop.IValueExpressionConstraint; /** - * BOpConstraint that wraps a {@link BooleanValueExpression}. + * {@link Constraint} wraps a {@link BooleanValueExpression}. */ public class Constraint<X> extends BOpBase implements IValueExpressionConstraint<X> { @@ -66,9 +66,8 @@ /** * Required shallow copy constructor. */ - public Constraint(final BOp[] args, - final Map<String, Object> anns) { - + public Constraint(final BOp[] args, final Map<String, Object> anns) { + super(args, anns); if (args.length != 1 || args[0] == null) @@ -83,6 +82,7 @@ super(op); } + @Override @SuppressWarnings("unchecked") public IValueExpression<X> getValueExpression() { @@ -90,6 +90,7 @@ } + @Override public boolean accept(final IBindingSet bs) { // try { Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/controller/HTreeNamedSubqueryOp.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/controller/HTreeNamedSubqueryOp.java 2014-01-07 22:10:34 UTC (rev 7746) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/controller/HTreeNamedSubqueryOp.java 2014-01-08 15:14:09 UTC (rev 7747) @@ -73,7 +73,7 @@ * * @author <a href="mailto:tho...@us...">Bryan Thompson</a> */ -public class HTreeNamedSubqueryOp extends PipelineOp { +public class HTreeNamedSubqueryOp extends PipelineOp implements INamedSubqueryOp { static private final transient Logger log = Logger .getLogger(HTreeNamedSubqueryOp.class); @@ -151,7 +151,7 @@ } - public HTreeNamedSubqueryOp(final BOp[] args, NV... annotations) { + public HTreeNamedSubqueryOp(final BOp[] args, final NV... annotations) { this(args, NV.asMap(annotations)); @@ -164,6 +164,7 @@ } + @Override public FutureTask<Void> eval(final BOpContext<IBindingSet> context) { return new FutureTask<Void>(new ControllerTask(this, context)); @@ -266,6 +267,7 @@ /** * Evaluate. */ + @Override public Void call() throws Exception { try { @@ -356,6 +358,7 @@ } + @Override public Void call() throws Exception { // The subquery Copied: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/controller/INamedSubqueryOp.java (from rev 7746, branches/BIGDATA_RELEASE_1_3_0/bigdata/src/java/com/bigdata/bop/controller/INamedSubqueryOp.java) =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/controller/INamedSubqueryOp.java (rev 0) +++ branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/controller/INamedSubqueryOp.java 2014-01-08 15:14:09 UTC (rev 7747) @@ -0,0 +1,42 @@ +/** + +Copyright (C) SYSTAP, LLC 2006-2010. All rights reserved. + +Contact: + SYSTAP, LLC + 4501 Tower Road + Greensboro, NC 27410 + lic...@bi... + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; version 2 of the License. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ +package com.bigdata.bop.controller; + +import com.bigdata.bop.join.SolutionSetHashJoinOp; + +/** + * Marker interface for named subquery evaluation. Solutions from the pipeline + * flow through this operator without modification. The subquery is evaluated + * exactly once, the first time this operator is invoked, and the solutions for + * the subquery are written onto a hash index. Those solutions are then joined + * back within the query at latter points in the query plan using a solution set + * hash join. + * + * @see SolutionSetHashJoinOp + * + * @author <a href="mailto:tho...@us...">Bryan Thompson</a> + */ +public interface INamedSubqueryOp { + +} Modified: branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/controller/JVMNamedSubqueryOp.java =================================================================== --- branches/MGC_1_3_0/bigdata/src/java/com/bigdata/bop/controller/JVMNamedSubqueryOp.java 2014-01-07 22:10:34 UTC (rev 7746) +++ branches/MGC_1_3_0/... [truncated message content] |
From: <mar...@us...> - 2014-03-07 17:42:46
|
Revision: 7917 http://sourceforge.net/p/bigdata/code/7917 Author: martyncutcher Date: 2014-03-07 17:42:40 +0000 (Fri, 07 Mar 2014) Log Message: ----------- merge main branch and add initial HA1 and HA5 tests Modified Paths: -------------- branches/MGC_1_3_0/.classpath branches/MGC_1_3_0/bigdata/src/java/com/bigdata/btree/Node.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/journal/CommitCounterUtility.java branches/MGC_1_3_0/bigdata/src/java/com/bigdata/search/FullTextIndex.java branches/MGC_1_3_0/bigdata/src/test/com/bigdata/journal/TestCommitCounterUtility.java branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/journal/jini/ha/HARestore.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/AbstractHA3JournalServerTestCase.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/AbstractHAJournalServerTestCase.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHA3ChangeLeader.java branches/MGC_1_3_0/bigdata-perf/bsbm3/build.properties branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/lexicon/BigdataValueCentricFullTextIndex.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/cache/DescribeBindingsCollector.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/cache/DescribeCacheUpdater.java branches/MGC_1_3_0/bigdata-rdf/src/java/com/bigdata/rdf/sparql/ast/eval/ASTEvalHelper.java branches/MGC_1_3_0/build.properties branches/MGC_1_3_0/build.xml branches/MGC_1_3_0/src/resources/HAJournal/HAJournal.config Added Paths: ----------- branches/MGC_1_3_0/EMC/ branches/MGC_1_3_0/EMC/bigdata/ branches/MGC_1_3_0/EMC/bigdata/sample/ branches/MGC_1_3_0/EMC/bigdata/sample/BloatTest.java branches/MGC_1_3_0/EMC/history retention.txt branches/MGC_1_3_0/EMC/zero retention.txt branches/MGC_1_3_0/bigdata-jini/src/java/com/bigdata/journal/jini/ha/NoSnapshotException.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/AbstractHA5JournalServerTestCase.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/HAJournal-D.config branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/HAJournal-E.config branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHA1JournalServer.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/TestHA5JournalServer.java branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/log4j-template-D.properties branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/log4j-template-E.properties branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/zkClient1.config branches/MGC_1_3_0/bigdata-jini/src/test/com/bigdata/journal/jini/ha/zkClient5.config Modified: branches/MGC_1_3_0/.classpath =================================================================== --- branches/MGC_1_3_0/.classpath 2014-03-06 22:38:54 UTC (rev 7916) +++ branches/MGC_1_3_0/.classpath 2014-03-07 17:42:40 UTC (rev 7917) @@ -31,6 +31,7 @@ <classpathentry kind="src" path="bigdata-gom/src/samples"/> <classpathentry kind="src" path="bigdata-gas/src/java"/> <classpathentry kind="src" path="bigdata-gas/src/test"/> + <classpathentry kind="src" path="EMC"/> <classpathentry exported="true" kind="lib" path="bigdata/lib/dsi-utils-1.0.6-020610.jar"/> <classpathentry exported="true" kind="lib" path="bigdata/lib/lgpl-utils-1.0.6-020610.jar"/> <classpathentry kind="lib" path="bigdata-jini/lib/apache/zookeeper-3.3.3.jar"/> Added: branches/MGC_1_3_0/EMC/bigdata/sample/BloatTest.java =================================================================== --- branches/MGC_1_3_0/EMC/bigdata/sample/BloatTest.java (rev 0) +++ branches/MGC_1_3_0/EMC/bigdata/sample/BloatTest.java 2014-03-07 17:42:40 UTC (rev 7917) @@ -0,0 +1,195 @@ + +package bigdata.sample; + +import java.io.File; +import java.io.FileWriter; +import java.io.IOException; +import java.io.PrintWriter; +import java.util.ArrayList; +import java.util.List; +import java.util.Properties; + +import junit.framework.TestCase; + +import org.openrdf.model.Literal; +import org.openrdf.model.URI; +import org.openrdf.model.ValueFactory; +import org.openrdf.repository.Repository; +import org.openrdf.repository.RepositoryConnection; +import org.openrdf.repository.RepositoryException; + +import com.bigdata.journal.DumpJournal; +import com.bigdata.journal.Journal; +import com.bigdata.journal.RWStrategy; +import com.bigdata.rdf.sail.BigdataSail; +import com.bigdata.rdf.sail.BigdataSailRepository; +import com.bigdata.rdf.store.AbstractTripleStore; +import com.bigdata.rwstore.RWStore; + +public class BloatTest extends TestCase { + + private static final int NUM_LOOPS = 40; + private static final int NUM_ITEMS = 10000; + private static final int NUM_STATIC_STATEMENTS = 13; + private static final long SLEEP_MILLIS = 10; // was 1000, but no need to sleep when testing journal commitsS + + public void test() throws RepositoryException, InterruptedException, IOException { + final File jnlFile = new File("/volumes/NonSSD/bigdata/emc/bloat.jnl"); + + if (jnlFile.exists()) { + jnlFile.delete(); + } + + Properties props = new Properties(); + props.setProperty("com.bigdata.rdf.sail.namespace", "topology.kb"); + props.setProperty("com.bigdata.journal.AbstractJournal.bufferMode", "DiskRW"); + props.setProperty("com.bigdata.btree.writeRetentionQueue.capacity", "4000"); + props.setProperty("com.bigdata.btree.BTree.branchingFactor", "128"); + props.setProperty("com.bigdata.service.AbstractTransactionService.minReleaseAge", "1"); // set to zero to avoid mess with history + props.setProperty("com.bigdata.rdf.store.AbstractTripleStore.textIndex", "false"); + props.setProperty( + "com.bigdata.rdf.rules.InferenceEngine.forwardChainOwlTransitiveProperty", "false"); + props.setProperty("com.bigdata.rdf.rules.InferenceEngine.forwardChainOwlSameAsClosure", + "false"); + props.setProperty("com.bigdata.rdf.rules.InferenceEngine.forwardChainOwlSameAsProperties", + "false"); + props.setProperty("com.bigdata.rdf.rules.InferenceEngine.forwardChainOwlInverseOf", "false"); + props.setProperty("com.bigdata.rdf.rules.InferenceEngine.forwardChainOwlEquivalentClass", + "false"); + props.setProperty( + "com.bigdata.rdf.rules.InferenceEngine.forwardChainOwlEquivalentProperty", "false"); + props.setProperty("com.bigdata.rdf.rules.InferenceEngine.forwardChainOwlHasValue", "false"); + props.setProperty("com.bigdata.rdf.rules.InferenceEngine.forwardChainRdfTypeRdfsResource", + "false"); + props.setProperty("com.bigdata.rdf.store.AbstractTripleStore.axiomsClass", + "com.bigdata.rdf.axioms.NoAxioms"); + props.setProperty("com.bigdata.rdf.sail.truthMaintenance", "false"); + props.setProperty("com.bigdata.rdf.store.AbstractTripleStore.justify", "false"); + props.setProperty("com.bigdata.rdf.store.AbstractTripleStore.statementIdentifiers", "false"); + props.setProperty("com.bigdata.rdf.store.AbstractTripleStore.quadsMode", "true"); + props.setProperty("com.bigdata.journal.AbstractJournal.maximumExtent", "209715200"); + props.setProperty("com.bigdata.service.IBigdataClient.collectPlatformStatistics", "false"); + props.setProperty("com.bigdata.service.IBigdataClient.httpdPort", "-1"); + // props.setProperty("com.bigdata.rdf.sail.bufferCapacity", "100000"); + props.setProperty("com.bigdata.rdf.sail.bufferCapacity", "100000"); + props.setProperty("com.bigdata.rdf.store.AbstractTripleStore.bloomFilter", "false"); + + props.setProperty(BigdataSail.Options.CREATE_TEMP_FILE, Boolean.FALSE.toString()); + props.setProperty(BigdataSail.Options.FILE, jnlFile.toString()); + + BigdataSail sail = new BigdataSail(props); + Repository repo = new BigdataSailRepository(sail); + repo.initialize(); + + final AbstractTripleStore store = sail.getDatabase(); + final Journal jrnl = ((Journal) store.getIndexManager()); + final RWStrategy rwstrat = (RWStrategy) jrnl.getBufferStrategy(); + final RWStore rw = rwstrat.getStore(); + + { + final StringBuilder sb = new StringBuilder(); + sb.append(storeStats(rw)); + //rw.showAllocators(sb); + + System.err.println(sb.toString()); + + } + + long prevBytes = 0; + for (int loop = 0; loop < NUM_LOOPS; ++loop) { + RepositoryConnection conn = repo.getConnection(); + conn.setAutoCommit(false); + + if (loop == 0) { + applyInitialStatements(conn); + } else { + applyChurningStatements(conn); + } + + long currBytes = jnlFile.length(); + if (currBytes > prevBytes) { + System.err.println("Loop " + loop + " journal file is " + currBytes + + " bytes <------ JUMP!"); + + prevBytes = currBytes; + } + conn.commit(); + conn.close(); + + if (loop % 20 == 0) { + System.out.println("Loop " + loop + " journal file is " + currBytes + " bytes"); + final StringBuilder sb = new StringBuilder(); + sb.append(storeStats(rw)); + // rw.showAllocators(sb); + + System.err.println(sb.toString()); + + // dumpJournal(loop, 128, jrnl); + } + + Thread.sleep(SLEEP_MILLIS); + } + + { + final StringBuilder sb = new StringBuilder(); + sb.append(storeStats(rw)); + rw.showAllocators(sb); + + System.err.println(sb.toString()); + // dumpJournal(NUM_LOOPS, 128, jrnl); + } + + } + + private String storeStats(final RWStore rw) { + final long allocs = rw.getTotalAllocations(); + final long frees = rw.getTotalFrees(); + + return "RW allocations: " + allocs + ", frees: " + frees + ", net: " + (allocs-frees) + "\n"; + } + + private void applyInitialStatements(RepositoryConnection conn) throws RepositoryException { + System.out.println("Applying initial statements"); + ValueFactory vf = conn.getValueFactory(); + for (int item = 0; item < NUM_ITEMS; ++item) { + URI c = vf.createURI("context:item" + item); + URI s = vf.createURI("subject:item" + item); + for (int x = 0; x < NUM_STATIC_STATEMENTS; ++x) { + URI p = vf.createURI("predicate:" + x); + Literal o = vf.createLiteral("SomeValue"); + conn.add(s, p, o, c); + } + } + } + + private void applyChurningStatements(RepositoryConnection conn) throws RepositoryException { + ValueFactory vf = conn.getValueFactory(); + for (int item = 0; item < NUM_ITEMS; ++item) { + URI s = vf.createURI("context:item" + item); + URI p = vf.createURI("predicate:lastUpdateTime"); + conn.remove(s, p, null); + conn.add(s, p, vf.createLiteral(System.currentTimeMillis())); + } + + } + + private void dumpJournal(final int loop, final int bf, final Journal journal) throws IOException { + final File file = new File("/volumes/NonSSD/bigdata/emc/dumpJournal_loop_" + loop + "_bf_" + bf + ".txt"); + + final PrintWriter writer = new PrintWriter(new FileWriter(file)); + + final List<String> nsList = new ArrayList<String>(); + + nsList.add("topology.kb"); + + final DumpJournal dumpJournal = new DumpJournal(journal); + + dumpJournal.dumpJournal(writer, nsList, false, true, true, false); + + writer.close(); + + System.err.println("DumpJournal written to " + file.getAbsolutePath()); + + + } +} Added: branches/MGC_1_3_0/EMC/history retention.txt =================================================================== --- branches/MGC_1_3_0/EMC/history retention.txt (rev 0) +++ branches/MGC_1_3_0/EMC/history retention.txt 2014-03-07 17:42:40 UTC (rev 7917) @@ -0,0 +1,307 @@ + +BIGDATA(R) + + Flexible + Reliable + Affordable + Web-Scale Computing for the Enterprise + +Copyright SYSTAP, LLC 2006-2013. All rights reserved. + +192.168.0.4 +Tue Feb 25 10:30:24 GMT 2014 +Mac OS X/10.9 x86_64 +Mac OS X 10.9 x86_64 #CPU=8 +Oracle Corporation 1.7.0_11 +freeMemory=9734656 +buildVersion=1.3.0 + +Dependency License +ICU http://source.icu-project.org/repos/icu/icu/trunk/license.html +bigdata-ganglia http://www.apache.org/licenses/LICENSE-2.0.html +colt http://acs.lbl.gov/software/colt/license.html +commons-codec http://www.apache.org/licenses/LICENSE-2.0.html +commons-fileupload http://www.apache.org/licenses/LICENSE-2.0.html +commons-io http://www.apache.org/licenses/LICENSE-2.0.html +commons-logging http://www.apache.org/licenses/LICENSE-2.0.html +dsiutils http://www.gnu.org/licenses/lgpl-2.1.html +fastutil http://www.apache.org/licenses/LICENSE-2.0.html +flot http://www.opensource.org/licenses/mit-license.php +high-scale-lib http://creativecommons.org/licenses/publicdomain +httpclient http://www.apache.org/licenses/LICENSE-2.0.html +httpclient-cache http://www.apache.org/licenses/LICENSE-2.0.html +httpcore http://www.apache.org/licenses/LICENSE-2.0.html +httpmime http://www.apache.org/licenses/LICENSE-2.0.html +jetty http://www.apache.org/licenses/LICENSE-2.0.html +jquery https://github.com/jquery/jquery/blob/master/MIT-LICENSE.txt +log4j http://www.apache.org/licenses/LICENSE-2.0.html +lucene http://www.apache.org/licenses/LICENSE-2.0.html +nanohttp http://elonen.iki.fi/code/nanohttpd/#license +nxparser http://sw.deri.org/2006/08/nxparser/license.txt +river http://www.apache.org/licenses/LICENSE-2.0.html +servlet-api http://www.apache.org/licenses/LICENSE-2.0.html +sesame http://www.openrdf.org/download.jsp +slf4j http://www.slf4j.org/license.html +zookeeper http://www.apache.org/licenses/LICENSE-2.0.html + +INFO: com.bigdata.util.config.LogUtil: Configure: file:/Users/mgc/Eclipse/workspace/BIGDATA_ALLURA_1_3_0/bin/log4j.properties +WARN : 0 main info.aduna.lang.service.ServiceRegistry.<init>(ServiceRegistry.java:47): New service class org.openrdf.rio.rdfxml.RDFXMLParserFactory replaces existing service class com.bigdata.rdf.rio.rdfxml.BigdataRDFXMLParserFactory +WARN : 10 main info.aduna.lang.service.ServiceRegistry.<init>(ServiceRegistry.java:47): New service class org.openrdf.rio.rdfxml.RDFXMLWriterFactory replaces existing service class com.bigdata.rdf.rio.rdfxml.BigdataRDFXMLWriterFactory +allocations: 59, frees: 14, net: 45, commits: 1 + +------------------------- +RWStore Allocator Summary +------------------------- +AllocatorSize AllocatorCount SlotsAllocated %SlotsAllocated SlotsRecycled SlotChurn SlotsInUse %SlotsInUse MeanAllocation SlotsReserved %SlotsUnused BytesReserved BytesAppData %SlotWaste %AppData %StoreFile %TotalWaste %FileWaste +64 1 10 16.95 1 1.11 9 20.00 37 1024 99.12 65536 337 99.49 1.50 4.17 4.21 4.15 +128 1 1 1.69 0 1.00 1 2.22 81 512 99.80 65536 81 99.88 0.36 4.17 4.22 4.16 +192 1 2 3.39 0 1.00 2 4.44 161 1024 99.80 196608 323 99.84 1.44 12.50 12.66 12.48 +320 1 26 44.07 13 2.00 13 28.89 224 1024 98.73 327680 2964 99.10 13.19 20.83 20.94 20.64 +512 1 2 3.39 0 1.00 2 4.44 385 256 99.22 131072 770 99.41 3.43 8.33 8.40 8.28 +768 0 0 0.00 0 0.00 0 0.00 0 0 0.00 0 0 0.00 0.00 0.00 0.00 0.00 +1024 1 12 20.34 0 1.00 12 26.67 817 256 95.31 262144 9804 96.26 43.62 16.67 16.28 16.04 +2048 1 6 10.17 0 1.00 6 13.33 1366 256 97.66 524288 8198 98.44 36.47 33.33 33.29 32.81 +3072 0 0 0.00 0 0.00 0 0.00 0 0 0.00 0 0 0.00 0.00 0.00 0.00 0.00 +4096 0 0 0.00 0 0.00 0 0.00 0 0 0.00 0 0 0.00 0.00 0.00 0.00 0.00 +8192 0 0 0.00 0 0.00 0 0.00 0 0 0.00 0 0 0.00 0.00 0.00 0.00 0.00 + +------------------------- +BLOBS +------------------------- +Bucket(K) Allocations Allocated Deletes Deleted Current Data Mean Churn +16 0 0 0 0 0 0 0 0.00 +32 0 0 0 0 0 0 0 0.00 +64 0 0 0 0 0 0 0 0.00 +128 0 0 0 0 0 0 0 0.00 +256 0 0 0 0 0 0 0 0.00 +512 0 0 0 0 0 0 0 0.00 +1024 0 0 0 0 0 0 0 0.00 +2048 0 0 0 0 0 0 0 0.00 +4096 0 0 0 0 0 0 0 0.00 +8192 0 0 0 0 0 0 0 0.00 +16384 0 0 0 0 0 0 0 0.00 +32768 0 0 0 0 0 0 0 0.00 +65536 0 0 0 0 0 0 0 0.00 +2097151 0 0 0 0 0 0 0 0.00 + +Applying initial statements +Loop 0 journal file is 90177536 bytes <------ JUMP! +Loop 0 journal file is 90177536 bytes +allocations: 33058, frees: 16, net: 33042, commits: 2 + +------------------------- +RWStore Allocator Summary +------------------------- +AllocatorSize AllocatorCount SlotsAllocated %SlotsAllocated SlotsRecycled SlotChurn SlotsInUse %SlotsInUse MeanAllocation SlotsReserved %SlotsUnused BytesReserved BytesAppData %SlotWaste %AppData %StoreFile %TotalWaste %FileWaste +64 3 20010 60.53 1 1.00 20009 60.56 23 20480 2.30 1310720 478117 63.52 3.05 4.82 7.24 3.06 +128 1 4 0.01 0 1.00 4 0.01 89 512 99.22 65536 359 99.45 0.00 0.24 0.57 0.24 +192 1 3 0.01 0 1.00 3 0.01 151 1024 99.71 196608 455 99.77 0.00 0.72 1.71 0.72 +320 1 37 0.11 14 1.61 23 0.07 224 1024 97.75 327680 5344 98.37 0.03 1.20 2.80 1.19 +512 1 7 0.02 0 1.00 7 0.02 424 256 97.27 131072 2974 97.73 0.02 0.48 1.11 0.47 +768 1 2034 6.15 0 1.00 2034 6.16 608 2048 0.68 1572864 1237913 21.30 7.88 5.78 2.91 1.23 +1024 1 44 0.13 0 1.00 44 0.13 903 256 82.81 262144 39771 84.83 0.25 0.96 1.93 0.82 +2048 2 10900 32.97 1 1.00 10899 32.99 1274 11008 0.99 22544384 13891705 38.38 88.48 82.89 75.26 31.81 +3072 1 19 0.06 0 1.00 19 0.06 2295 256 92.58 786432 43616 94.45 0.28 2.89 6.46 2.73 +4096 0 0 0.00 0 0.00 0 0.00 0 0 0.00 0 0 0.00 0.00 0.00 0.00 0.00 +8192 0 0 0.00 0 0.00 0 0.00 0 0 0.00 0 0 0.00 0.00 0.00 0.00 0.00 + +------------------------- +BLOBS +------------------------- +Bucket(K) Allocations Allocated Deletes Deleted Current Data Mean Churn +16 0 0 0 0 0 0 0 0.00 +32 0 0 0 0 0 0 0 0.00 +64 0 0 0 0 0 0 0 0.00 +128 0 0 0 0 0 0 0 0.00 +256 0 0 0 0 0 0 0 0.00 +512 0 0 0 0 0 0 0 0.00 +1024 0 0 0 0 0 0 0 0.00 +2048 0 0 0 0 0 0 0 0.00 +4096 0 0 0 0 0 0 0 0.00 +8192 0 0 0 0 0 0 0 0.00 +16384 0 0 0 0 0 0 0 0.00 +32768 0 0 0 0 0 0 0 0.00 +65536 0 0 0 0 0 0 0 0.00 +2097151 0 0 0 0 0 0 0 0.00 + +Loop 20 journal file is 90177536 bytes +allocations: 128582, frees: 80142, net: 48440, commits: 22 + +------------------------- +RWStore Allocator Summary +------------------------- +AllocatorSize AllocatorCount SlotsAllocated %SlotsAllocated SlotsRecycled SlotChurn SlotsInUse %SlotsInUse MeanAllocation SlotsReserved %SlotsUnused BytesReserved BytesAppData %SlotWaste %AppData %StoreFile %TotalWaste %FileWaste +64 3 20032 15.58 27 1.00 20005 41.30 23 20480 2.32 1310720 478225 63.51 1.21 1.90 2.84 1.21 +128 1 25 0.02 20 5.00 5 0.01 97 512 99.02 65536 539 99.18 0.00 0.10 0.22 0.09 +192 1 4 0.00 1 1.33 3 0.01 146 1024 99.71 196608 441 99.78 0.00 0.29 0.67 0.28 +320 1 220 0.17 190 7.33 30 0.06 224 1024 97.07 327680 9716 97.03 0.02 0.48 1.08 0.46 +512 1 87 0.07 54 2.64 33 0.07 430 256 87.11 131072 14277 89.11 0.04 0.19 0.40 0.17 +768 1 5138 4.00 72 1.01 5066 10.46 650 5120 1.05 3932160 3293934 16.23 8.33 5.71 2.18 0.93 +1024 1 132 0.10 36 1.38 96 0.20 863 256 62.50 262144 82883 68.38 0.21 0.38 0.61 0.26 +2048 4 102701 79.87 79544 4.43 23157 47.81 1462 28672 19.23 58720256 35537604 39.48 89.83 85.25 79.08 33.66 +3072 1 155 0.12 120 4.43 35 0.07 2490 256 86.33 786432 91066 88.42 0.23 1.14 2.37 1.01 +4096 1 48 0.04 42 8.00 6 0.01 3334 256 97.66 1048576 20462 98.05 0.05 1.52 3.51 1.49 +8192 1 40 0.03 36 10.00 4 0.01 8192 256 98.44 2097152 32912 98.43 0.08 3.04 7.04 3.00 + +------------------------- +BLOBS +------------------------- +Bucket(K) Allocations Allocated Deletes Deleted Current Data Mean Churn +16 0 0 0 0 0 0 0 0.00 +32 0 0 18 320052 -18 -320052 0 0.00 +64 0 0 0 0 0 0 0 0.00 +128 0 0 0 0 0 0 0 0.00 +256 0 0 0 0 0 0 0 0.00 +512 0 0 0 0 0 0 0 0.00 +1024 0 0 0 0 0 0 0 0.00 +2048 0 0 0 0 0 0 0 0.00 +4096 0 0 0 0 0 0 0 0.00 +8192 0 0 0 0 0 0 0 0.00 +16384 0 0 0 0 0 0 0 0.00 +32768 0 0 0 0 0 0 0 0.00 +65536 0 0 0 0 0 0 0 0.00 +2097151 0 0 0 0 0 0 0 0.00 + +Loop 40 journal file is 90177536 bytes +allocations: 224082, frees: 169482, net: 54600, commits: 42 + +------------------------- +RWStore Allocator Summary +------------------------- +AllocatorSize AllocatorCount SlotsAllocated %SlotsAllocated SlotsRecycled SlotChurn SlotsInUse %SlotsInUse MeanAllocation SlotsReserved %SlotsUnused BytesReserved BytesAppData %SlotWaste %AppData %StoreFile %TotalWaste %FileWaste +64 3 20052 8.95 47 1.00 20005 36.64 23 20480 2.32 1310720 478225 63.51 1.00 1.53 2.18 0.97 +128 1 45 0.02 40 9.00 5 0.01 97 512 99.02 65536 567 99.13 0.00 0.08 0.17 0.08 +192 1 4 0.00 1 1.33 3 0.01 146 1024 99.71 196608 441 99.78 0.00 0.23 0.51 0.23 +320 1 400 0.18 370 13.33 30 0.05 224 1024 97.07 327680 12516 96.18 0.03 0.38 0.82 0.37 +512 1 167 0.07 114 3.15 53 0.10 431 256 79.30 131072 22937 82.50 0.05 0.15 0.28 0.13 +768 2 8288 3.70 152 1.02 8136 14.90 660 8192 0.68 6291456 5377105 14.53 11.27 7.32 2.39 1.06 +1024 1 170 0.08 75 1.79 95 0.17 863 256 62.89 262144 82050 68.70 0.17 0.31 0.47 0.21 +2048 5 194506 86.80 168278 7.42 26228 48.04 1473 35840 26.82 73400320 41591889 43.34 87.18 85.43 83.25 37.02 +3072 1 275 0.12 242 8.33 33 0.06 2478 256 87.11 786432 83201 89.42 0.17 0.92 1.84 0.82 +4096 1 95 0.04 87 11.88 8 0.01 3337 256 96.88 1048576 27327 97.39 0.06 1.22 2.67 1.19 +8192 1 80 0.04 76 20.00 4 0.01 8192 256 98.44 2097152 33072 98.42 0.07 2.44 5.40 2.40 + +------------------------- +BLOBS +------------------------- +Bucket(K) Allocations Allocated Deletes Deleted Current Data Mean Churn +16 0 0 0 0 0 0 0 0.00 +32 0 0 38 677012 -38 -677012 0 0.00 +64 0 0 0 0 0 0 0 0.00 +128 0 0 0 0 0 0 0 0.00 +256 0 0 0 0 0 0 0 0.00 +512 0 0 0 0 0 0 0 0.00 +1024 0 0 0 0 0 0 0 0.00 +2048 0 0 0 0 0 0 0 0.00 +4096 0 0 0 0 0 0 0 0.00 +8192 0 0 0 0 0 0 0 0.00 +16384 0 0 0 0 0 0 0 0.00 +32768 0 0 0 0 0 0 0 0.00 +65536 0 0 0 0 0 0 0 0.00 +2097151 0 0 0 0 0 0 0 0.00 + +Loop 60 journal file is 90177536 bytes +allocations: 319582, frees: 258822, net: 60760, commits: 62 + +------------------------- +RWStore Allocator Summary +------------------------- +AllocatorSize AllocatorCount SlotsAllocated %SlotsAllocated SlotsRecycled SlotChurn SlotsInUse %SlotsInUse MeanAllocation SlotsReserved %SlotsUnused BytesReserved BytesAppData %SlotWaste %AppData %StoreFile %TotalWaste %FileWaste +64 3 20072 6.28 67 1.00 20005 32.92 23 20480 2.32 1310720 478225 63.51 0.86 1.48 2.52 0.94 +128 1 65 0.02 60 13.00 5 0.01 98 512 99.02 65536 598 99.09 0.00 0.07 0.20 0.07 +192 1 4 0.00 1 1.33 3 0.00 146 1024 99.71 196608 441 99.78 0.00 0.22 0.59 0.22 +320 1 580 0.18 550 19.33 30 0.05 224 1024 97.07 327680 15316 95.33 0.03 0.37 0.95 0.35 +512 1 247 0.08 174 3.38 73 0.12 431 256 71.48 131072 31597 75.89 0.06 0.15 0.30 0.11 +768 2 11438 3.58 232 1.02 11206 18.44 664 11264 0.51 8650752 7451419 13.86 13.47 9.80 3.64 1.36 +1024 1 210 0.07 114 2.19 96 0.16 864 256 62.50 262144 83109 68.30 0.15 0.30 0.54 0.20 +2048 5 286324 89.59 257025 9.77 29299 48.22 1477 35840 18.25 73400320 47100812 35.83 85.18 83.15 79.75 29.79 +3072 1 383 0.12 350 11.61 33 0.05 2476 256 87.11 786432 82989 89.45 0.15 0.89 2.13 0.80 +4096 1 139 0.04 133 23.17 6 0.01 3336 256 97.66 1048576 20585 98.04 0.04 1.19 3.12 1.16 +8192 1 120 0.04 116 30.00 4 0.01 8192 256 98.44 2097152 33232 98.42 0.06 2.38 6.26 2.34 + +------------------------- +BLOBS +------------------------- +Bucket(K) Allocations Allocated Deletes Deleted Current Data Mean Churn +16 0 0 0 0 0 0 0 0.00 +32 0 0 58 1033972 -58 -1033972 0 0.00 +64 0 0 0 0 0 0 0 0.00 +128 0 0 0 0 0 0 0 0.00 +256 0 0 0 0 0 0 0 0.00 +512 0 0 0 0 0 0 0 0.00 +1024 0 0 0 0 0 0 0 0.00 +2048 0 0 0 0 0 0 0 0.00 +4096 0 0 0 0 0 0 0 0.00 +8192 0 0 0 0 0 0 0 0.00 +16384 0 0 0 0 0 0 0 0.00 +32768 0 0 0 0 0 0 0 0.00 +65536 0 0 0 0 0 0 0 0.00 +2097151 0 0 0 0 0 0 0 0.00 + +Loop 72 journal file is 177799168 bytes <------ JUMP! +Loop 80 journal file is 177799168 bytes +allocations: 415082, frees: 348162, net: 66920, commits: 82 + +------------------------- +RWStore Allocator Summary +------------------------- +AllocatorSize AllocatorCount SlotsAllocated %SlotsAllocated SlotsRecycled SlotChurn SlotsInUse %SlotsInUse MeanAllocation SlotsReserved %SlotsUnused BytesReserved BytesAppData %SlotWaste %AppData %StoreFile %TotalWaste %FileWaste +64 3 20092 4.84 87 1.00 20005 29.89 23 20480 2.32 1310720 478225 63.51 0.76 1.24 1.95 0.79 +128 1 85 0.02 80 17.00 5 0.01 98 512 99.02 65536 614 99.06 0.00 0.06 0.15 0.06 +192 1 4 0.00 1 1.33 3 0.00 146 1024 99.71 196608 441 99.78 0.00 0.19 0.46 0.19 +320 1 760 0.18 730 25.33 30 0.04 224 1024 97.07 327680 18116 94.47 0.03 0.31 0.73 0.29 +512 1 327 0.08 234 3.52 93 0.14 431 256 63.67 131072 40257 69.29 0.06 0.12 0.21 0.09 +768 2 14588 3.51 312 1.02 14276 21.33 666 14336 0.42 11010048 9519526 13.54 15.20 10.45 3.49 1.42 +1024 1 249 0.06 153 2.59 96 0.14 864 256 62.50 262144 83127 68.29 0.13 0.25 0.42 0.17 +2048 6 378147 91.10 345777 11.68 32370 48.37 1479 43008 24.73 88080384 52363294 40.55 83.60 83.63 83.69 33.91 +3072 1 482 0.12 450 15.06 32 0.05 2474 256 87.50 786432 79509 89.89 0.13 0.75 1.66 0.67 +4096 1 188 0.05 182 31.33 6 0.01 3333 256 97.66 1048576 20184 98.08 0.03 1.00 2.41 0.98 +8192 1 160 0.04 156 40.00 4 0.01 8192 256 98.44 2097152 33392 98.41 0.05 1.99 4.84 1.96 + +------------------------- +BLOBS +------------------------- +Bucket(K) Allocations Allocated Deletes Deleted Current Data Mean Churn +16 0 0 0 0 0 0 0 0.00 +32 0 0 78 1390932 -78 -1390932 0 0.00 +64 0 0 0 0 0 0 0 0.00 +128 0 0 0 0 0 0 0 0.00 +256 0 0 0 0 0 0 0 0.00 +512 0 0 0 0 0 0 0 0.00 +1024 0 0 0 0 0 0 0 0.00 +2048 0 0 0 0 0 0 0 0.00 +4096 0 0 0 0 0 0 0 0.00 +8192 0 0 0 0 0 0 0 0.00 +16384 0 0 0 0 0 0 0 0.00 +32768 0 0 0 0 0 0 0 0.00 +65536 0 0 0 0 0 0 0 0.00 +2097151 0 0 0 0 0 0 0 0.00 + +allocations: 505806, frees: 433035, net: 72771, commits: 101 + +------------------------- +RWStore Allocator Summary +------------------------- +AllocatorSize AllocatorCount SlotsAllocated %SlotsAllocated SlotsRecycled SlotChurn SlotsInUse %SlotsInUse MeanAllocation SlotsReserved %SlotsUnused BytesReserved BytesAppData %SlotWaste %AppData %StoreFile %TotalWaste %FileWaste +64 3 20111 3.98 106 1.01 20005 27.49 23 20480 2.32 1310720 478225 63.51 0.69 1.22 2.18 0.77 +128 1 104 0.02 99 20.80 5 0.01 98 512 99.02 65536 628 99.04 0.00 0.06 0.17 0.06 +192 1 4 0.00 1 1.33 3 0.00 146 1024 99.71 196608 441 99.78 0.00 0.18 0.51 0.18 +320 1 931 0.18 901 31.03 30 0.04 224 1024 97.07 327680 20776 93.66 0.03 0.30 0.80 0.29 +512 1 403 0.08 291 3.60 112 0.15 431 256 56.25 131072 48484 63.01 0.07 0.12 0.22 0.08 +768 3 17579 3.48 388 1.02 17191 23.62 667 17408 1.25 13369344 11484364 14.10 16.53 12.42 4.94 1.75 +1024 1 286 0.06 189 2.95 97 0.13 864 256 62.11 262144 83877 68.00 0.12 0.24 0.47 0.17 +2048 6 465382 92.01 430096 13.19 35286 48.49 1480 43008 17.95 88080384 57230575 35.02 82.37 81.80 80.77 28.65 +3072 1 575 0.11 545 19.17 30 0.04 2475 256 88.28 786432 75336 90.42 0.11 0.73 1.86 0.66 +4096 1 233 0.05 225 29.13 8 0.01 3334 256 96.88 1048576 27015 97.42 0.04 0.97 2.67 0.95 +8192 1 198 0.04 194 49.50 4 0.01 8192 256 98.44 2097152 33544 98.40 0.05 1.95 5.40 1.92 + +Visited 0 tuples in 0ms +Visited 20016 tuples in 112ms +Visited 20016 tuples in 7ms +Visited 140000 tuples in 33ms +Visited 140000 tuples in 30ms +Visited 140000 tuples in 28ms +Visited 140000 tuples in 32ms +Visited 140000 tuples in 49ms +Visited 140000 tuples in 28ms +DumpJournal written to /volumes/NonSSD/bigdata/emc/dumpJournal_loop_100_bf_128.txt Added: branches/MGC_1_3_0/EMC/zero retention.txt =================================================================== --- branches/MGC_1_3_0/EMC/zero retention.txt (rev 0) +++ branches/MGC_1_3_0/EMC/zero retention.txt 2014-03-07 17:42:40 UTC (rev 7917) @@ -0,0 +1,114 @@ +allocations: 33068, frees: 36, net: 33032, commits: 2 +allocations: 34891, frees: 630, net: 34261, commits: 4 +allocations: 36606, frees: 1728, net: 34878, commits: 6 +allocations: 38322, frees: 2826, net: 35496, commits: 8 +allocations: 40037, frees: 3925, net: 36112, commits: 10 +allocations: 40895, frees: 4474, net: 36421, commits: 11 + + +This run maintained the connection, and showed no change, so creating and closing a connec n makes no difference + +allocations: 33068, frees: 36, net: 33032, commits: 2 +allocations: 34891, frees: 630, net: 34261, commits: 4 +allocations: 36606, frees: 1728, net: 34878, commits: 6 +allocations: 40037, frees: 3925, net: 36112, commits: 10 +allocations: 40895, frees: 4474, net: 36421, commits: 11 + + +Loop 2 journal file is 90177536 bytes +RW allocations: 34891, frees: 630, net: 34261, commits: 4, BTree recycles: 622, allocations: 34804 (34182) + +------------------------- +RWStore Allocator Summary +------------------------- +AllocatorSize AllocatorCount SlotsAllocated %SlotsAllocated SlotsRecycled SlotChurn SlotsInUse %SlotsInUse MeanAllocation SlotsReserved %SlotsUnused BytesReserved BytesAppData %SlotWaste %AppData %StoreFile %TotalWaste %FileWaste +64 3 20012 57.36 9 1.00 20003 58.38 23 20480 2.33 1310720 477936 63.54 2.69 4.18 6.10 2.65 +128 1 8 0.02 5 2.67 3 0.01 103 512 99.41 65536 347 99.47 0.00 0.21 0.48 0.21 +192 1 2 0.01 0 1.00 2 0.01 161 1024 99.80 196608 323 99.84 0.00 0.63 1.44 0.63 +320 1 57 0.16 44 4.38 13 0.04 224 1024 98.73 327680 3496 98.93 0.02 1.04 2.37 1.03 +512 1 9 0.03 3 1.50 6 0.02 397 256 97.66 131072 2240 98.29 0.01 0.42 0.94 0.41 +768 1 2049 5.87 12 1.01 2037 5.95 608 2048 0.54 1572864 1239919 21.17 6.99 5.01 2.44 1.06 +1024 1 84 0.24 5 1.06 79 0.23 943 256 69.14 262144 74808 71.46 0.42 0.84 1.37 0.60 +2048 2 12389 35.51 507 1.04 11882 34.68 1302 12544 5.28 25690112 15307541 40.41 86.29 81.84 76.05 33.07 +3072 1 205 0.59 29 1.16 176 0.51 2307 256 31.25 786432 400890 49.02 2.26 2.51 2.82 1.23 +4096 1 76 0.22 16 1.27 60 0.18 3844 256 76.56 1048576 232770 77.80 1.31 3.34 5.98 2.60 +8192 0 0 0.00 0 0.00 0 0.00 0 0 0.00 0 0 0.00 0.00 0.00 0.00 0.00 + + +RW allocations: 40895, frees: 4474, net: 36421, commits: 11, BTree recycles: 4444, allocations: 40711 (36267) + +RW increase: 2160 vs BTree increase: 2079 + +RW allocations: 40037, frees: 3925, net: 36112, commits: 10, BTree recycles: 3899, allocations: 39875 (35976) +RW allocations: 40895, frees: 4474, net: 36421, commits: 11, BTree recycles: 4445, allocations: 40721 (36276) +RW Net: 309 +BTree Net: 300 + +So there is an amount not accounted for, but BTree is main culprit + +RW allocations: 34891, frees: 630, net: 34261, commits: 4, BTree recycles: 622, allocations: 34807, newNodes: 14803 +RW allocations: 36606, frees: 1728, net: 34878, commits: 6, BTree recycles: 1714 (1092), allocations: 36495 (1688), newNodes: 16493 (1690) +RW allocations: 38322, frees: 2826, net: 35496, commits: 8, BTree recycles: 2806 (1092), allocations: 38184 (1689), newNodes: 18185 (1692) + + +RW allocations: 38322, frees: 2826, net: 35496, commits: 8, BTree recycles: 2806, allocations: 38177, newNodes: 18181, rawDels: 0 +RW allocations: 40037, frees: 3925, net: 36112, commits: 10, BTree recycles: 3899, allocations: 39859, newNodes: 19867, rawDels: 0 +RW allocations: 40895, frees: 4474, net: 36421, commits: 11, BTree recycles: 4445, allocations: 40705, newNodes: 20712, rawDels: 0 + +So this looks odd. Looks like it never recycles? So where do the recycles come from? + +Called from replaceChildRef .. copyOnWrite ... nowhere ... [truncated message content] |