Fix NPOIFS creation of an empty filesystem, with create/write/read test
git-svn-id: https://svn.apache.org/repos/asf/poi/trunk@1102482 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
parent
62b5690d8f
commit
26ea0d987d
@ -93,20 +93,38 @@ public class NPOIFSFileSystem extends BlockStore
|
|||||||
private POIFSBigBlockSize bigBlockSize =
|
private POIFSBigBlockSize bigBlockSize =
|
||||||
POIFSConstants.SMALLER_BIG_BLOCK_SIZE_DETAILS;
|
POIFSConstants.SMALLER_BIG_BLOCK_SIZE_DETAILS;
|
||||||
|
|
||||||
|
private NPOIFSFileSystem(boolean newFS)
|
||||||
|
{
|
||||||
|
_header = new HeaderBlock(bigBlockSize);
|
||||||
|
_property_table = new NPropertyTable(_header);
|
||||||
|
_mini_store = new NPOIFSMiniStore(this, _property_table.getRoot(), new ArrayList<BATBlock>(), _header);
|
||||||
|
_xbat_blocks = new ArrayList<BATBlock>();
|
||||||
|
_bat_blocks = new ArrayList<BATBlock>();
|
||||||
|
_root = null;
|
||||||
|
|
||||||
|
if(newFS) {
|
||||||
|
// Data needs to initially hold just the header block,
|
||||||
|
// a single bat block, and an empty properties section
|
||||||
|
_data = new ByteArrayBackedDataSource(new byte[bigBlockSize.getBigBlockSize()*3]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Constructor, intended for writing
|
* Constructor, intended for writing
|
||||||
*/
|
*/
|
||||||
public NPOIFSFileSystem()
|
public NPOIFSFileSystem()
|
||||||
{
|
{
|
||||||
_header = new HeaderBlock(bigBlockSize);
|
this(true);
|
||||||
_property_table = new NPropertyTable(_header);
|
|
||||||
_mini_store = new NPOIFSMiniStore(this, _property_table.getRoot(), new ArrayList<BATBlock>(), _header);
|
// Mark us as having a single empty BAT at offset 0
|
||||||
_xbat_blocks = new ArrayList<BATBlock>();
|
_header.setBATCount(1);
|
||||||
_bat_blocks = new ArrayList<BATBlock>();
|
_header.setBATArray(new int[] { 0 });
|
||||||
_root = null;
|
_bat_blocks.add(BATBlock.createEmptyBATBlock(bigBlockSize, false));
|
||||||
|
setNextBlock(0, POIFSConstants.FAT_SECTOR_BLOCK);
|
||||||
|
|
||||||
// Data needs to initially hold just the header block
|
// Now associate the properties with the empty block
|
||||||
_data = new ByteArrayBackedDataSource(new byte[bigBlockSize.getBigBlockSize()]);
|
_property_table.setStartBlock(1);
|
||||||
|
setNextBlock(1, POIFSConstants.END_OF_CHAIN);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -169,7 +187,7 @@ public class NPOIFSFileSystem extends BlockStore
|
|||||||
private NPOIFSFileSystem(FileChannel channel, boolean closeChannelOnError)
|
private NPOIFSFileSystem(FileChannel channel, boolean closeChannelOnError)
|
||||||
throws IOException
|
throws IOException
|
||||||
{
|
{
|
||||||
this();
|
this(false);
|
||||||
|
|
||||||
try {
|
try {
|
||||||
// Get the header
|
// Get the header
|
||||||
@ -230,7 +248,7 @@ public class NPOIFSFileSystem extends BlockStore
|
|||||||
public NPOIFSFileSystem(InputStream stream)
|
public NPOIFSFileSystem(InputStream stream)
|
||||||
throws IOException
|
throws IOException
|
||||||
{
|
{
|
||||||
this();
|
this(false);
|
||||||
|
|
||||||
ReadableByteChannel channel = null;
|
ReadableByteChannel channel = null;
|
||||||
boolean success = false;
|
boolean success = false;
|
||||||
@ -674,7 +692,7 @@ public class NPOIFSFileSystem extends BlockStore
|
|||||||
{
|
{
|
||||||
// HeaderBlock
|
// HeaderBlock
|
||||||
HeaderBlockWriter hbw = new HeaderBlockWriter(_header);
|
HeaderBlockWriter hbw = new HeaderBlockWriter(_header);
|
||||||
hbw.writeBlock( getBlockAt(0) );
|
hbw.writeBlock( getBlockAt(-1) );
|
||||||
|
|
||||||
// BATs
|
// BATs
|
||||||
for(BATBlock bat : _bat_blocks) {
|
for(BATBlock bat : _bat_blocks) {
|
||||||
|
@ -17,6 +17,8 @@
|
|||||||
|
|
||||||
package org.apache.poi.poifs.filesystem;
|
package org.apache.poi.poifs.filesystem;
|
||||||
|
|
||||||
|
import java.io.ByteArrayInputStream;
|
||||||
|
import java.io.ByteArrayOutputStream;
|
||||||
import java.nio.ByteBuffer;
|
import java.nio.ByteBuffer;
|
||||||
import java.util.Iterator;
|
import java.util.Iterator;
|
||||||
|
|
||||||
@ -534,8 +536,31 @@ public final class TestNPOIFSFileSystem extends TestCase {
|
|||||||
* Then, add some streams, write and read
|
* Then, add some streams, write and read
|
||||||
*/
|
*/
|
||||||
public void testCreateWriteRead() throws Exception {
|
public void testCreateWriteRead() throws Exception {
|
||||||
|
NPOIFSFileSystem fs = new NPOIFSFileSystem();
|
||||||
|
|
||||||
|
// Initially has a BAT but not SBAT
|
||||||
|
assertEquals(POIFSConstants.FAT_SECTOR_BLOCK, fs.getNextBlock(0));
|
||||||
|
assertEquals(POIFSConstants.END_OF_CHAIN, fs.getNextBlock(1));
|
||||||
|
assertEquals(POIFSConstants.UNUSED_BLOCK, fs.getNextBlock(2));
|
||||||
|
|
||||||
|
// Check that the SBAT is empty
|
||||||
|
assertEquals(POIFSConstants.END_OF_CHAIN, fs.getRoot().getProperty().getStartBlock());
|
||||||
|
|
||||||
|
// Write and read it
|
||||||
|
ByteArrayOutputStream baos = new ByteArrayOutputStream();
|
||||||
|
fs.writeFilesystem(baos);
|
||||||
|
fs = new NPOIFSFileSystem(new ByteArrayInputStream(baos.toByteArray()));
|
||||||
|
|
||||||
|
// Check it's still like that
|
||||||
|
assertEquals(POIFSConstants.FAT_SECTOR_BLOCK, fs.getNextBlock(0));
|
||||||
|
assertEquals(POIFSConstants.END_OF_CHAIN, fs.getNextBlock(1));
|
||||||
|
assertEquals(POIFSConstants.UNUSED_BLOCK, fs.getNextBlock(2));
|
||||||
|
assertEquals(POIFSConstants.END_OF_CHAIN, fs.getRoot().getProperty().getStartBlock());
|
||||||
|
|
||||||
|
// Now add a normal stream and a mini stream
|
||||||
// TODO
|
// TODO
|
||||||
// TODO
|
|
||||||
|
// TODO The rest of the test
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO Directory/Document write tests
|
// TODO Directory/Document write tests
|
||||||
|
@ -828,12 +828,12 @@ public final class TestNPOIFSStream extends TestCase {
|
|||||||
NPOIFSFileSystem fs = new NPOIFSFileSystem();
|
NPOIFSFileSystem fs = new NPOIFSFileSystem();
|
||||||
NPOIFSStream stream = new NPOIFSStream(fs);
|
NPOIFSStream stream = new NPOIFSStream(fs);
|
||||||
|
|
||||||
// Check our filesystem has a single block
|
// Check our filesystem has a BAT and the Properties
|
||||||
// to hold the BAT
|
assertEquals(2, fs.getFreeBlock());
|
||||||
assertEquals(1, fs.getFreeBlock());
|
|
||||||
BATBlock bat = fs.getBATBlockAndIndex(0).getBlock();
|
BATBlock bat = fs.getBATBlockAndIndex(0).getBlock();
|
||||||
assertEquals(POIFSConstants.FAT_SECTOR_BLOCK, bat.getValueAt(0));
|
assertEquals(POIFSConstants.FAT_SECTOR_BLOCK, bat.getValueAt(0));
|
||||||
assertEquals(POIFSConstants.UNUSED_BLOCK, bat.getValueAt(1));
|
assertEquals(POIFSConstants.END_OF_CHAIN, bat.getValueAt(1));
|
||||||
|
assertEquals(POIFSConstants.UNUSED_BLOCK, bat.getValueAt(2));
|
||||||
|
|
||||||
// Check the stream as-is
|
// Check the stream as-is
|
||||||
assertEquals(POIFSConstants.END_OF_CHAIN, stream.getStartBlock());
|
assertEquals(POIFSConstants.END_OF_CHAIN, stream.getStartBlock());
|
||||||
@ -853,12 +853,13 @@ public final class TestNPOIFSStream extends TestCase {
|
|||||||
stream.updateContents(data);
|
stream.updateContents(data);
|
||||||
|
|
||||||
// Check now
|
// Check now
|
||||||
assertEquals(3, fs.getFreeBlock());
|
assertEquals(4, fs.getFreeBlock());
|
||||||
bat = fs.getBATBlockAndIndex(0).getBlock();
|
bat = fs.getBATBlockAndIndex(0).getBlock();
|
||||||
assertEquals(POIFSConstants.FAT_SECTOR_BLOCK, bat.getValueAt(0));
|
assertEquals(POIFSConstants.FAT_SECTOR_BLOCK, bat.getValueAt(0));
|
||||||
assertEquals(2, bat.getValueAt(1));
|
assertEquals(POIFSConstants.END_OF_CHAIN, bat.getValueAt(1));
|
||||||
assertEquals(POIFSConstants.END_OF_CHAIN, bat.getValueAt(2));
|
assertEquals(3, bat.getValueAt(2));
|
||||||
assertEquals(POIFSConstants.UNUSED_BLOCK, bat.getValueAt(3));
|
assertEquals(POIFSConstants.END_OF_CHAIN, bat.getValueAt(3));
|
||||||
|
assertEquals(POIFSConstants.UNUSED_BLOCK, bat.getValueAt(4));
|
||||||
|
|
||||||
|
|
||||||
Iterator<ByteBuffer> it = stream.getBlockIterator();
|
Iterator<ByteBuffer> it = stream.getBlockIterator();
|
||||||
|
Loading…
Reference in New Issue
Block a user