/******************************************************************************* * Copyright (c) 2008 Scott Stanchfield. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at * http://www.eclipse.org/legal/epl-v10.html * * Contributors: * Based on the ANTLR parser generator by Terence Parr, http://antlr.org * Ric Klaren <klaren@cs.utwente.nl> * Scott Stanchfield - Modifications for XML Parsing *******************************************************************************/ package com.javadude.antxr; /** A circular buffer object used by CharBuffer */ public class CharQueue { /** Physical circular buffer of tokens */ protected char[] buffer; /** buffer.length-1 for quick modulos */ private int sizeLessOne; /** physical index of front token */ private int offset; /** number of tokens in the queue */ protected int nbrEntries; public CharQueue(int minSize) { // Find first power of 2 >= to requested size int size; if ( minSize<0 ) { init(16); // pick some value for them return; } // check for overflow if ( minSize>=(Integer.MAX_VALUE/2) ) { init(Integer.MAX_VALUE); // wow that's big. return; } for (size = 2; size < minSize; size *= 2) { // nothing } init(size); } /** Add token to end of the queue * @param tok The token to add */ public final void append(char tok) { if (nbrEntries == buffer.length) { expand(); } buffer[(offset + nbrEntries) & sizeLessOne] = tok; nbrEntries++; } /** Fetch a token from the queue by index * @param idx The index of the token to fetch, where zero is the token at the front of the queue */ public final char elementAt(int idx) { return buffer[(offset + idx) & sizeLessOne]; } /** Expand the token buffer by doubling its capacity */ private final void expand() { char[] newBuffer = new char[buffer.length * 2]; // Copy the contents to the new buffer // Note that this will store the first logical item in the // first physical array element. for (int i = 0; i < buffer.length; i++) { newBuffer[i] = elementAt(i); } // Re-initialize with new contents, keep old nbrEntries buffer = newBuffer; sizeLessOne = buffer.length - 1; offset = 0; } /** Initialize the queue. * @param size The initial size of the queue */ public void init(int size) { // Allocate buffer buffer = new char[size]; // Other initialization sizeLessOne = size - 1; offset = 0; nbrEntries = 0; } /** Clear the queue. Leaving the previous buffer alone. */ public final void reset() { offset = 0; nbrEntries = 0; } /** Remove char from front of queue */ public final void removeFirst() { offset = (offset + 1) & sizeLessOne; nbrEntries--; } }