Author: toad
Date: 2006-07-26 20:49:32 +0000 (Wed, 26 Jul 2006)
New Revision: 9784
Modified:
trunk/freenet/src/freenet/client/async/SplitFileInserterSegment.java
trunk/freenet/src/freenet/node/Version.java
Log:
909: More work on resumable inserts.
Modified: trunk/freenet/src/freenet/client/async/SplitFileInserterSegment.java
===================================================================
--- trunk/freenet/src/freenet/client/async/SplitFileInserterSegment.java
2006-07-26 20:19:17 UTC (rev 9783)
+++ trunk/freenet/src/freenet/client/async/SplitFileInserterSegment.java
2006-07-26 20:49:32 UTC (rev 9784)
@@ -69,7 +69,7 @@
if(!"SplitFileInserterSegment".equals(fs.get("Type")))
throw new ResumeException("Wrong Type:
"+fs.get("Type"));
finished = Fields.stringToBool(fs.get("Finished"), false);
- encoded = Fields.stringToBool(fs.get("Encoded"), false);
+ encoded = true;
started = Fields.stringToBool(fs.get("Started"), false);
SimpleFieldSet errorsFS = fs.subset("Errors");
if(errorsFS != null)
@@ -97,38 +97,10 @@
dataBlocks = new Bucket[dataBlockCount];
dataURIs = new FreenetURI[dataBlockCount];
dataBlockInserters = new SingleBlockInserter[dataBlockCount];
- for(int i=0;i<dataBlockCount;i++) {
- SimpleFieldSet blockFS =
dataFS.subset(Integer.toString(i));
- if(blockFS == null) throw new ResumeException("No data
block "+i+" on segment "+segNo);
- tmp = blockFS.get("URI");
- if(tmp != null) {
- try {
- dataURIs[i] = new FreenetURI(tmp);
- blocksGotURI++;
- } catch (MalformedURLException e) {
- throw new ResumeException("Corrupt URI:
"+e+" : "+tmp);
- }
- } else hasURIs = false;
- boolean blockFinished =
Fields.stringToBool(blockFS.get("Finished"), false);
- if(blockFinished && dataURIs[i] == null)
- throw new ResumeException("Block "+i+" of
"+segNo+" finished but no URI");
- if(!blockFinished) {
- finished = false;
- // Read data
- SimpleFieldSet bucketFS =
blockFS.subset("Data");
- if(bucketFS == null)
- throw new ResumeException("Block "+i+"
of "+segNo+" not finished but no data");
- try {
- dataBlocks[i] =
SerializableToFieldSetBucketUtil.create(bucketFS, ctx.random,
ctx.persistentFileTracker);
- } catch (CannotCreateFromFieldSetException e) {
- throw new ResumeException("Failed to
deserialize block "+i+" of "+segNo+" : "+e, e);
- }
- if(dataBlocks[i] == null)
- throw new ResumeException("Block "+i+"
of "+segNo+" not finished but no data (create returned null)");
- // Don't create fetcher yet; that happens in
start()
- } else blocksCompleted++;
- }
+ // Check blocks first, because if there are missing check
blocks, we need
+ // all the data blocks so we can re-encode.
+
SimpleFieldSet checkFS = fs.subset("CheckBlocks");
if(checkFS != null) {
tmp = checkFS.get("Count");
@@ -157,31 +129,31 @@
} catch (MalformedURLException e) {
throw new
ResumeException("Corrupt URI: "+e+" : "+tmp);
}
- } else hasURIs = false;
- boolean blockFinished =
Fields.stringToBool(blockFS.get("Finished"), false);
- if(blockFinished && checkURIs[i] == null)
- throw new ResumeException("Check block
"+i+" of "+segNo+" finished but no URI");
- if(blockFinished && !encoded)
- throw new ResumeException("Check block
"+i+" of "+segNo+" finished but not encoded");
+ } else {
+ hasURIs = false;
+ encoded = false;
+ }
+ boolean blockFinished =
Fields.stringToBool(blockFS.get("Finished"), false) && checkURIs[i] != null;
+ // Read data; only necessary if the block isn't
finished.
if(!blockFinished) {
- // Read data
SimpleFieldSet bucketFS =
blockFS.subset("Data");
- if(bucketFS == null)
- throw new
ResumeException("Check block "+i+" of "+segNo+" not finished but no data");
- try {
- checkBlocks[i] =
SerializableToFieldSetBucketUtil.create(bucketFS, ctx.random,
ctx.persistentFileTracker);
- } catch
(CannotCreateFromFieldSetException e) {
- Logger.error(this, "Failed to
deserialize check block "+i+" of "+segNo+" : "+e, e);
- // Re-encode it.
- checkBlocks[i] = null;
- encoded = false;
+ if(bucketFS != null) {
+ try {
+ checkBlocks[i] =
SerializableToFieldSetBucketUtil.create(bucketFS, ctx.random,
ctx.persistentFileTracker);
+ } catch
(CannotCreateFromFieldSetException e) {
+ Logger.error(this,
"Failed to deserialize check block "+i+" of "+segNo+" : "+e, e);
+ // Re-encode it.
+ checkBlocks[i] = null;
+ encoded = false;
+ }
+ if(checkBlocks[i] == null)
+ throw new
ResumeException("Check block "+i+" of "+segNo+" not finished but no data
(create returned null)");
}
- if(checkBlocks[i] == null)
- throw new
ResumeException("Check block "+i+" of "+segNo+" not finished but no data
(create returned null)");
// Don't create fetcher yet; that happens in
start()
} else blocksCompleted++;
- if(checkBlocks[i] == null && checkURIs[i] ==
null)
+ if(checkBlocks[i] == null && checkURIs[i] ==
null) {
encoded = false;
+ }
}
splitfileAlgo = FECCodec.getCodec(splitfileAlgorithm,
dataBlockCount, checkBlocks.length);
} else {
@@ -193,6 +165,46 @@
this.checkBlockInserters = new
SingleBlockInserter[checkBlocksCount];
hasURIs = false;
}
+
+ for(int i=0;i<dataBlockCount;i++) {
+ SimpleFieldSet blockFS =
dataFS.subset(Integer.toString(i));
+ if(blockFS == null) throw new ResumeException("No data
block "+i+" on segment "+segNo);
+ tmp = blockFS.get("URI");
+ if(tmp != null) {
+ try {
+ dataURIs[i] = new FreenetURI(tmp);
+ blocksGotURI++;
+ } catch (MalformedURLException e) {
+ throw new ResumeException("Corrupt URI:
"+e+" : "+tmp);
+ }
+ } else hasURIs = false;
+ boolean blockFinished =
Fields.stringToBool(blockFS.get("Finished"), false);
+ if(blockFinished && dataURIs[i] == null)
+ throw new ResumeException("Block "+i+" of
"+segNo+" finished but no URI");
+ if(!blockFinished)
+ finished = false;
+ else
+ blocksCompleted++;
+
+ // Read data
+ SimpleFieldSet bucketFS = blockFS.subset("Data");
+ if(bucketFS == null) {
+ if(!blockFinished)
+ throw new ResumeException("Block "+i+"
of "+segNo+" not finished but no data");
+ else if(splitfileAlgorithm > 0 && !encoded)
+ throw new ResumeException("Block "+i+"
of "+segNo+" data not available even though not encoded");
+ } else {
+ try {
+ dataBlocks[i] =
SerializableToFieldSetBucketUtil.create(bucketFS, ctx.random,
ctx.persistentFileTracker);
+ } catch (CannotCreateFromFieldSetException e) {
+ throw new ResumeException("Failed to
deserialize block "+i+" of "+segNo+" : "+e, e);
+ }
+ if(dataBlocks[i] == null)
+ throw new ResumeException("Block "+i+"
of "+segNo+" could not serialize data (create returned null) from "+bucketFS);
+ // Don't create fetcher yet; that happens in
start()
+ }
+ }
+
if(!encoded) {
finished = false;
hasURIs = false;
@@ -253,7 +265,7 @@
SingleBlockInserter sbi =
checkBlockInserters[i];
// If encoded, then sbi == null => block finished
- boolean finished = encoded && sbi == null;
+ boolean finished = encoded && sbi == null &&
checkURIs[i] != null;
if(encoded) {
block.put("Finished", finished);
}
@@ -310,6 +322,7 @@
}
}
if(encoded) {
+ onEncodedSegment();
parent.encodedSegment(this);
}
if(hasURIs) {
@@ -345,18 +358,7 @@
// Because of the counting.
encoded = true;
parent.encodedSegment(this);
- synchronized(this) {
- for(int i=0;i<dataBlockInserters.length;i++) {
- if(dataBlockInserters[i] == null &&
dataBlocks[i] != null) {
- try {
-
parent.ctx.persistentBucketFactory.freeBucket(dataBlocks[i]);
- } catch (IOException e) {
- Logger.error(this,
"Could not free "+dataBlocks[i]+" : "+e, e);
- }
- dataBlocks[i] = null;
- }
- }
- }
+ onEncodedSegment();
} catch (IOException e) {
InserterException ex =
new
InserterException(InserterException.BUCKET_ERROR, e, null);
@@ -369,6 +371,21 @@
}
}
+ private void onEncodedSegment() {
+ synchronized(this) {
+ for(int i=0;i<dataBlockInserters.length;i++) {
+ if(dataBlockInserters[i] == null &&
dataBlocks[i] != null) {
+ try {
+
parent.ctx.persistentBucketFactory.freeBucket(dataBlocks[i]);
+ } catch (IOException e) {
+ Logger.error(this, "Could not
free "+dataBlocks[i]+" : "+e, e);
+ }
+ dataBlocks[i] = null;
+ }
+ }
+ }
+ }
+
private void finish(InserterException ex) {
Logger.minor(this, "Finishing "+this+" with "+ex, ex);
synchronized(this) {
Modified: trunk/freenet/src/freenet/node/Version.java
===================================================================
--- trunk/freenet/src/freenet/node/Version.java 2006-07-26 20:19:17 UTC (rev
9783)
+++ trunk/freenet/src/freenet/node/Version.java 2006-07-26 20:49:32 UTC (rev
9784)
@@ -18,7 +18,7 @@
public static final String protocolVersion = "1.0";
/** The build number of the current revision */
- private static final int buildNumber = 908;
+ private static final int buildNumber = 909;
/** Oldest build of Fred we will talk to */
private static final int oldLastGoodBuild = 870;