1 19 20 package org.netbeans.lib.lexer; 21 22 import org.netbeans.lib.editor.util.ArrayUtilities; 23 import org.netbeans.lib.editor.util.CharSequenceUtilities; 24 import org.netbeans.lib.editor.util.CharSubSequence; 25 26 37 38 public abstract class PreprocessedTextStorage implements CharSequence { 39 40 41 private static final boolean testing = Boolean.getBoolean("netbeans.debug.lexer.test"); 42 43 56 public static PreprocessedTextStorage create(CharSequence rawText, 57 char[] preprocessedChars, int preprocessedCharsLength, 58 int preprocessedStartIndex, int[] preprocessedRawLengthShifts) { 59 char[] preprocessedCharsCopy = ArrayUtilities.charArray(preprocessedChars, preprocessedCharsLength); 60 int totalRawLengthShift = preprocessedRawLengthShifts[preprocessedCharsLength - 1]; 62 PreprocessedTextStorage storage; 64 if (totalRawLengthShift <= Byte.MAX_VALUE) { byte[] arr = new byte[preprocessedCharsLength]; 66 for (int i = preprocessedCharsLength - 1; i >= 0; i--) 67 arr[i] = (byte)preprocessedRawLengthShifts[i]; 68 storage = new ByteRawIndex(rawText, preprocessedCharsCopy, preprocessedStartIndex, 69 preprocessedCharsLength, totalRawLengthShift, arr); 70 71 } else if (totalRawLengthShift <= Short.MAX_VALUE) { short[] arr = new short[preprocessedCharsLength]; 73 for (int i = preprocessedCharsLength - 1; i >= 0; i--) 74 arr[i] = (short)preprocessedRawLengthShifts[i]; 75 storage = new ShortRawIndex(rawText, preprocessedCharsCopy, preprocessedStartIndex, 76 preprocessedCharsLength, totalRawLengthShift, arr); 77 78 } else { int[] arr = new int[preprocessedCharsLength]; 80 System.arraycopy(preprocessedChars, 0, arr, 0, preprocessedCharsLength); 81 storage = new IntRawIndex(rawText, preprocessedCharsCopy, preprocessedStartIndex, 82 preprocessedCharsLength, totalRawLengthShift, arr); 83 } 84 85 if (testing) 86 storage.consistencyCheck(); 87 return storage; 88 } 89 90 103 public static PreprocessedTextStorage create(CharSequence rawText, char[] preprocessedChars, int preprocessedCharsLength, 104 int preprocessedStartIndex, int[] preprocessedRawLengthShifts, 105 char[] extraPreprocessedChars, int[] extraRawLengthShifts, int preStartIndex, int postEndIndex) { 106 int extraPreCharsLength = (extraPreprocessedChars.length - preStartIndex); 107 preprocessedStartIndex -= extraPreCharsLength; 108 int length = extraPreCharsLength + preprocessedCharsLength + postEndIndex; 109 110 char[] preprocessedCharsCopy = new char[length]; 112 System.arraycopy(extraPreprocessedChars, preStartIndex, preprocessedCharsCopy, 0, extraPreCharsLength); 113 System.arraycopy(preprocessedChars, 0, preprocessedCharsCopy, extraPreCharsLength, preprocessedCharsLength); 114 System.arraycopy(extraPreprocessedChars, 0, preprocessedCharsCopy, extraPreCharsLength + preprocessedCharsLength, postEndIndex); 115 116 int totalRawLengthShift = (postEndIndex > 0) 118 ? extraRawLengthShifts[postEndIndex - 1] 119 : (preprocessedCharsLength > 0) 120 ? preprocessedRawLengthShifts[preprocessedCharsLength - 1] 121 : extraRawLengthShifts[extraPreprocessedChars.length - 1]; 123 124 125 126 int ind = length - 1; 128 PreprocessedTextStorage storage; 129 if (totalRawLengthShift <= Byte.MAX_VALUE) { byte[] arr = new byte[length]; 131 for (int i = postEndIndex - 1; i >= 0; i--) 132 arr[ind--] = (byte)extraRawLengthShifts[i]; 133 for (int i = preprocessedCharsLength - 1; i >= 0; i--) 134 arr[ind--] = (byte)preprocessedRawLengthShifts[i]; 135 for (int i = extraPreprocessedChars.length - 1; i >= preStartIndex; i--) 136 arr[ind--] = (byte)extraRawLengthShifts[i]; 137 storage = new ByteRawIndex(rawText, preprocessedCharsCopy, preprocessedStartIndex, length, totalRawLengthShift, arr); 138 139 } else if (totalRawLengthShift <= Short.MAX_VALUE) { short[] arr = new short[length]; 141 for (int i = postEndIndex - 1; i >= 0; i--) 142 arr[ind--] = (short)extraRawLengthShifts[i]; 143 for (int i = preprocessedCharsLength - 1; i >= 0; i--) 144 arr[ind--] = (short)preprocessedRawLengthShifts[i]; 145 for (int i = extraPreprocessedChars.length - 1; i >= preStartIndex; i--) 146 arr[ind--] = (short)extraRawLengthShifts[i]; 147 storage = new ShortRawIndex(rawText, preprocessedCharsCopy, preprocessedStartIndex, length, totalRawLengthShift, arr); 148 149 } else { int[] arr = new int[length]; 153 for (int i = postEndIndex - 1; i >= 0; i--) 154 arr[ind--] = extraRawLengthShifts[i]; 155 for (int i = preprocessedCharsLength - 1; i >= 0; i--) 156 arr[ind--] = preprocessedRawLengthShifts[i]; 157 for (int i = extraPreprocessedChars.length - 1; i >= preStartIndex; i--) 158 arr[ind--] = extraRawLengthShifts[i]; 159 storage = new IntRawIndex(rawText, preprocessedCharsCopy, preprocessedStartIndex, length, totalRawLengthShift, arr); 160 } 161 162 if (testing) 163 storage.consistencyCheck(); 164 return storage; 165 } 166 167 168 171 private final CharSequence rawText; 173 176 private final char[] preprocessedChars; 178 181 private final int preprocessedStartIndex; 183 186 private final int totalRawLengthShift; 188 193 private final int length; 195 protected PreprocessedTextStorage(CharSequence rawText, char[] preprocessedChars, 196 int preprocessedStartIndex, int length, int totalRawLengthShift) { 197 this.rawText = rawText; 198 this.preprocessedChars = preprocessedChars; 199 this.preprocessedStartIndex = preprocessedStartIndex; 200 this.totalRawLengthShift = totalRawLengthShift; 202 this.length = length; 203 } 204 205 protected abstract int prepRawLengthShift(int index); 206 207 213 public final int rawLength(int length) { 214 if (length > preprocessedStartIndex) { 215 int prepLength = length - preprocessedStartIndex; 216 if (prepLength <= preprocessedChars.length) { 217 length += prepRawLengthShift(prepLength - 1); 218 } else { 219 length += totalRawLengthShift; 220 } 221 } 222 return length; 223 } 224 225 231 public final int rawLengthShift(int index) { 232 if (index < preprocessedStartIndex) { 233 return index; 234 } else { 235 index -= preprocessedStartIndex; 236 if (index <= preprocessedChars.length) { 237 return prepRawLengthShift(index) ; 238 } else { return totalRawLengthShift; 240 } 241 } 242 } 243 244 public final char charAt(int index) { 245 CharSequenceUtilities.checkIndexValid(index, length); 246 if (index < preprocessedStartIndex) { 247 return rawText.charAt(index); 248 } else { 249 int prepIndex = index - preprocessedStartIndex; 250 if (prepIndex < preprocessedChars.length) { 251 return preprocessedChars[prepIndex]; 252 } else { return rawText.charAt(index + totalRawLengthShift); 254 } 255 } 256 } 257 258 public final CharSequence subSequence(int start, int end) { 259 return new CharSubSequence(this, start, end); 260 } 261 262 public final int length() { 263 return length; 264 } 265 266 private void consistencyCheck() { 267 int lastRLS = 0; 269 for (int i = 0; i < preprocessedChars.length; i++) { 270 int rls = prepRawLengthShift(i); 271 if (rls < lastRLS) { 272 throw new IllegalStateException ("rls=" + rls + " < lastRLS=" + lastRLS + " at index=" + i); } 275 lastRLS = rls; 276 } 277 } 278 279 private static final class ByteRawIndex extends PreprocessedTextStorage { 280 281 private final byte[] preprocessedRawLengthShifts; 283 ByteRawIndex(CharSequence rawText, char[] preprocessedChars, int preprocessedStartIndex, 284 int length, int totalRawLengthShift, byte[] preprocessedRawLengthShifts) { 285 super(rawText, preprocessedChars, preprocessedStartIndex, length, totalRawLengthShift); 286 this.preprocessedRawLengthShifts = preprocessedRawLengthShifts; 287 } 288 289 protected final int prepRawLengthShift(int index) { 290 return preprocessedRawLengthShifts[index]; 291 } 292 293 } 294 295 private static final class ShortRawIndex extends PreprocessedTextStorage { 296 297 private final short[] preprocessedRawLengthShifts; 299 ShortRawIndex(CharSequence rawText, char[] preprocessedChars, int preprocessedStartIndex, 300 int length, int totalRawLengthShift, short[] preprocessedRawLengthShifts) { 301 super(rawText, preprocessedChars, preprocessedStartIndex, length, totalRawLengthShift); 302 this.preprocessedRawLengthShifts = preprocessedRawLengthShifts; 303 } 304 305 protected final int prepRawLengthShift(int index) { 306 return preprocessedRawLengthShifts[index]; 307 } 308 309 } 310 311 private static final class IntRawIndex extends PreprocessedTextStorage { 312 313 private final int[] preprocessedRawLengthShifts; 315 IntRawIndex(CharSequence rawText, char[] preprocessedChars, int preprocessedStartIndex, 316 int length, int totalRawLengthShift, int[] preprocessedRawLengthShifts) { 317 super(rawText, preprocessedChars, preprocessedStartIndex, length, totalRawLengthShift); 318 this.preprocessedRawLengthShifts = preprocessedRawLengthShifts; 319 } 320 321 protected final int prepRawLengthShift(int index) { 322 return preprocessedRawLengthShifts[index]; 323 } 324 325 } 326 327 } 328 | Popular Tags |