001: /* ====================================================================
002: Licensed to the Apache Software Foundation (ASF) under one or more
003: contributor license agreements. See the NOTICE file distributed with
004: this work for additional information regarding copyright ownership.
005: The ASF licenses this file to You under the Apache License, Version 2.0
006: (the "License"); you may not use this file except in compliance with
007: the License. You may obtain a copy of the License at
008:
009: http://www.apache.org/licenses/LICENSE-2.0
010:
011: Unless required by applicable law or agreed to in writing, software
012: distributed under the License is distributed on an "AS IS" BASIS,
013: WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014: See the License for the specific language governing permissions and
015: limitations under the License.
016: ==================================================================== */
017:
018: package org.apache.poi.poifs.storage;
019:
020: import org.apache.poi.util.LittleEndian;
021: import org.apache.poi.util.LittleEndianConsts;
022:
023: import java.io.*;
024:
025: import java.util.*;
026:
027: /**
028: * Class LocalRawDataBlockList
029: *
030: * @author Marc Johnson(mjohnson at apache dot org)
031: */
032:
033: public class LocalRawDataBlockList extends RawDataBlockList {
034: private List _list;
035: private RawDataBlock[] _array;
036:
037: /**
038: * Constructor LocalRawDataBlockList
039: *
040: * @exception IOException
041: */
042:
043: public LocalRawDataBlockList() throws IOException {
044: super (new ByteArrayInputStream(new byte[0]));
045: _list = new ArrayList();
046: _array = null;
047: }
048:
049: /**
050: * create and a new XBAT block
051: *
052: * @param start index of first BAT block
053: * @param end index of last BAT block
054: * @param chain index of next XBAT block
055: *
056: * @exception IOException
057: */
058:
059: public void createNewXBATBlock(final int start, final int end,
060: final int chain) throws IOException {
061: byte[] data = new byte[512];
062: int offset = 0;
063:
064: for (int k = start; k <= end; k++) {
065: LittleEndian.putInt(data, offset, k);
066: offset += LittleEndianConsts.INT_SIZE;
067: }
068: while (offset != 508) {
069: LittleEndian.putInt(data, offset, -1);
070: offset += LittleEndianConsts.INT_SIZE;
071: }
072: LittleEndian.putInt(data, offset, chain);
073: add(new RawDataBlock(new ByteArrayInputStream(data)));
074: }
075:
076: /**
077: * create a BAT block and add it to the list
078: *
079: * @param start_index initial index for the block list
080: *
081: * @exception IOException
082: */
083:
084: public void createNewBATBlock(final int start_index)
085: throws IOException {
086: byte[] data = new byte[512];
087: int offset = 0;
088:
089: for (int j = 0; j < 128; j++) {
090: int index = start_index + j;
091:
092: if (index % 256 == 0) {
093: LittleEndian.putInt(data, offset, -1);
094: } else if (index % 256 == 255) {
095: LittleEndian.putInt(data, offset, -2);
096: } else {
097: LittleEndian.putInt(data, offset, index + 1);
098: }
099: offset += LittleEndianConsts.INT_SIZE;
100: }
101: add(new RawDataBlock(new ByteArrayInputStream(data)));
102: }
103:
104: /**
105: * fill the list with dummy blocks
106: *
107: * @param count of blocks
108: *
109: * @exception IOException
110: */
111:
112: public void fill(final int count) throws IOException {
113: int limit = 128 * count;
114:
115: for (int j = _list.size(); j < limit; j++) {
116: add(new RawDataBlock(new ByteArrayInputStream(new byte[0])));
117: }
118: }
119:
120: /**
121: * add a new block
122: *
123: * @param block new block to add
124: */
125:
126: public void add(RawDataBlock block) {
127: _list.add(block);
128: }
129:
130: /**
131: * override of remove method
132: *
133: * @param index of block to be removed
134: *
135: * @return desired block
136: *
137: * @exception IOException
138: */
139:
140: public ListManagedBlock remove(final int index) throws IOException {
141: ensureArrayExists();
142: RawDataBlock rvalue = null;
143:
144: try {
145: rvalue = _array[index];
146: if (rvalue == null) {
147: throw new IOException("index " + index + " is null");
148: }
149: _array[index] = null;
150: } catch (ArrayIndexOutOfBoundsException ignored) {
151: throw new IOException("Cannot remove block[ " + index
152: + " ]; out of range");
153: }
154: return rvalue;
155: }
156:
157: /**
158: * remove the specified block from the list
159: *
160: * @param index the index of the specified block; if the index is
161: * out of range, that's ok
162: */
163:
164: public void zap(final int index) {
165: ensureArrayExists();
166: if ((index >= 0) && (index < _array.length)) {
167: _array[index] = null;
168: }
169: }
170:
171: private void ensureArrayExists() {
172: if (_array == null) {
173: _array = (RawDataBlock[]) _list
174: .toArray(new RawDataBlock[0]);
175: }
176: }
177: }
|