/**
 *
 * Copyright 2004 Hiram Chirino
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 *
 **/
package org.codehaus.activemq.journal.impl;

import org.codehaus.activemq.journal.RecordLocation;

/**
 * Defines a where a record can be located in the Journal. 
 * 
 * @version $Revision: 1.1 $
 */
public class RecordLocationImpl implements RecordLocation {

	final private byte fileMangerId;
	final private byte segmentIndex;
	final private int segmentOffset;
	final private long sequenceId;
	
	public RecordLocationImpl(final byte fileMangerId, final byte segmentIndex,
			final int fileOffset, long sequenceId) {
		super();
		this.fileMangerId = fileMangerId;
		this.segmentIndex = segmentIndex;
		this.segmentOffset = fileOffset;
		this.sequenceId = sequenceId;
	}
	
	/**
	 * @param b
	 * @param segmentIndex2
	 * @param offset
	 */
	public RecordLocationImpl(final byte fileMangerId, final byte segmentIndex, final int fileOffset) {
		super();
		this.fileMangerId = fileMangerId;
		this.segmentIndex = segmentIndex;
		this.segmentOffset = fileOffset;
		this.sequenceId = -1;
	}

	/**
	 * @see java.lang.Comparable#compareTo(java.lang.Object)
	 */
	public int compareTo(Object o) {
		return (int)(sequenceId - ((RecordLocationImpl)o).sequenceId);
	}
	
	/**
	 * @see java.lang.Object#hashCode()
	 */
	public int hashCode() {
		return segmentOffset^segmentIndex^(fileMangerId<<8)^((int)sequenceId);
	}

	/**
	 * @see java.lang.Object#equals(java.lang.Object)
	 */
	public boolean equals(Object o) {
		if( o==null || o.getClass()!=RecordLocationImpl.class )
			return false;
		RecordLocationImpl rl = (RecordLocationImpl)o;
		return rl.sequenceId == this.sequenceId && rl.segmentOffset == this.segmentOffset &&
					rl.segmentIndex==this.segmentIndex && rl.fileMangerId == this.fileMangerId;
	}
	
	/**
	 * @see java.lang.Object#toString()
	 */
	public String toString() {
		return ""+fileMangerId+":"+segmentIndex+":"+segmentOffset+":"+sequenceId;
	}

	/**
	 * @return Returns the fileMangerId.
	 */
	public byte getFileMangerId() {
		return fileMangerId;
	}
	/**
	 * @return Returns the fileId.
	 */
	public byte getSegmentIndex() {
		return segmentIndex;
	}
	/**
	 * @return Returns the fileOffset.
	 */
	public int getSegmentOffset() {
		return segmentOffset;
	}
	
	/**
	 * @return Returns the sequenceId.
	 */
	public long getSequenceId() {
		return sequenceId;
	}	

	public RecordLocationImpl setSegmentIndexAndOffset(byte segmentIndex, int offset) {
		return new RecordLocationImpl(this.fileMangerId, segmentIndex, offset);
	}

	public RecordLocationImpl setSequence(long seq) {
		return new RecordLocationImpl(this.fileMangerId, this.segmentIndex, this.segmentOffset, seq);
	}
}
