View Javadoc

1   /*** 
2    * 
3    * Copyright 2004 Protique Ltd
4    * 
5    * Licensed under the Apache License, Version 2.0 (the "License"); 
6    * you may not use this file except in compliance with the License. 
7    * You may obtain a copy of the License at 
8    * 
9    * http://www.apache.org/licenses/LICENSE-2.0
10   * 
11   * Unless required by applicable law or agreed to in writing, software
12   * distributed under the License is distributed on an "AS IS" BASIS, 
13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 
14   * See the License for the specific language governing permissions and 
15   * limitations under the License. 
16   * 
17   **/
18  
19  package org.codehaus.activemq.util;
20  import java.util.LinkedList;
21  
22  /***
23   * Holder for many bitArrays - used for message audit
24   * 
25   * @version $Revision: 1.2 $
26   */
27  public class BitArrayBin {
28      private LinkedList list;
29      private int maxNumberOfArrays;
30      private int currentIndex;
31      private int firstIndex = -1;
32      private int firstBin = -1;
33      private int windowSize;
34  
35      /***
36       * Create a BitArrayBin to a certain window size (number of messages to keep)
37       * 
38       * @param windowSize
39       */
40      public BitArrayBin(int windowSize) {
41          this.windowSize = windowSize;
42          maxNumberOfArrays = ((windowSize + 1) / BitArray.LONG_SIZE) + 1;
43          maxNumberOfArrays = Math.max(maxNumberOfArrays, 1);
44          list = new LinkedList();
45          for (int i = 0;i < maxNumberOfArrays;i++) {
46              list.add(new BitArray());
47          }
48      }
49  
50      /***
51       * Set a bit
52       * 
53       * @param index
54       * @param value
55       * @return
56       */
57      public boolean setBit(long index, boolean value) {
58          boolean answer = true;
59          BitArray ba = getBitArray(index);
60          if (ba != null) {
61              int offset = getOffset(index);
62              if (offset >= 0) {
63                  answer = ba.set(offset, value);
64              }
65          }
66          return answer;
67      }
68  
69      /***
70       * Get the boolean value at the index
71       * 
72       * @param index
73       * @return true/false
74       */
75      public boolean getBit(long index) {
76          boolean answer = index >= firstIndex;
77          BitArray ba = getBitArray(index);
78          if (ba != null) {
79              int offset = getOffset(index);
80              if (offset >= 0) {
81                  answer = ba.get(offset);
82                  return answer;
83              }
84          }
85          else {
86              //gone passed range for previous bins so assume set
87              answer = true;
88          }
89          return answer;
90      }
91  
92      /***
93       * Get the BitArray for the index
94       * 
95       * @param index
96       * @return
97       */
98      private BitArray getBitArray(long index) {
99          int bin = getBin(index);
100         BitArray answer = null;
101         if (bin >= 0) {
102             if (firstIndex < 0) {
103                 firstIndex = 0;
104             }
105             if (bin >= list.size()) {
106                 list.removeFirst();
107                 firstIndex += BitArray.LONG_SIZE;
108                 list.add(new BitArray());
109                 bin = list.size() - 1;
110             }
111             answer = (BitArray) list.get(bin);
112         }
113         return answer;
114     }
115 
116     /***
117      * Get the index of the bin from the total index
118      * 
119      * @param index
120      * @return the index of the bin
121      */
122     private int getBin(long index) {
123         int answer = 0;
124         if (firstBin < 0) {
125             firstBin = 0;
126         }
127         else if (firstIndex >= 0) {
128             answer = (int) ((index - firstIndex) / BitArray.LONG_SIZE);
129         }
130         return answer;
131     }
132 
133     /***
134      * Get the offset into a bin from the total index
135      * 
136      * @param index
137      * @return the relative offset into a bin
138      */
139     private int getOffset(long index) {
140         int answer = 0;
141         if (firstIndex >= 0) {
142             //System.out.println("getOffset(" + index + ") firstIndex = " + firstIndex + " bin = " + getBin(index));
143             answer = (int) ((index - firstIndex) - (BitArray.LONG_SIZE * getBin(index)));
144         }
145         return answer;
146     }
147 }