/*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You 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 tests.util;
import java.util.Stack;
/**
* A stack to store the parameters of a call, as well as the call stack.
*/
public class CallVerificationStack extends Stack<Object> {
/*
* --------------------------------------------------------------------
* Class variables
* --------------------------------------------------------------------
*/
private static final long serialVersionUID = 1L;
// the singleton
private static final CallVerificationStack _instance = new CallVerificationStack();
/*
* --------------------------------------------------------------------
* Instance variables
* --------------------------------------------------------------------
*/
// the call stack, store StackTraceElement
private final Stack<StackTraceElement> callStack = new Stack<StackTraceElement>();
/*
* -------------------------------------------------------------------
* Constructors
* -------------------------------------------------------------------
*/
/**
* Can't be instantiated.
*/
private CallVerificationStack() {
// empty
}
/*
* -------------------------------------------------------------------
* Methods
* -------------------------------------------------------------------
*/
/**
* Gets the singleton instance.
*
* @return the singleton instance
*/
public static CallVerificationStack getInstance() {
return _instance;
}
/**
* Pushes the call stack.
*/
private void pushCallStack() {
StackTraceElement[] eles = (new Throwable()).getStackTrace();
int i;
for (i = 1; i < eles.length; i++) {
if (!eles[i].getClassName().equals(this.getClass().getName())) {
break;
}
}
this.callStack.push(eles[i]);
}
/**
* Gets the "current" calling class name.
*
* @return the "current" calling class name
*/
public String getCurrentSourceClass() {
return this.callStack.peek().getClassName();
}
/**
* Gets the "current" calling method name.
*
* @return the "current" calling method name
*/
public String getCurrentSourceMethod() {
return this.callStack.peek().getMethodName();
}
/**
* Clear the parameter stack and the call stack.
*/
@Override
public void clear() {
this.callStack.clear();
super.clear();
}
@Override
public Object push(Object o) {
pushCallStack();
return super.push(o);
}
/**
* Pushes a boolean onto the top of this stack.
*
* @param val the value to push
*/
public void push(boolean val) {
this.push(new BaseTypeWrapper(val));
}
/**
* Pushes a char onto the top of this stack.
*
* @param val the value to push
*/
public void push(char val) {
this.push(new BaseTypeWrapper(val));
}
/**
* Pushes a double onto the top of this stack.
*
* @param val the value to push
*/
public void push(double val) {
this.push(new BaseTypeWrapper(val));
}
/**
* Pushes a float onto the top of this stack.
*
* @param val the value to push
*/
public void push(float val) {
this.push(new BaseTypeWrapper(val));
}
/**
* Pushes an int onto the top of this stack.
*
* @param val the value to push
*/
public void push(int val) {
this.push(new BaseTypeWrapper(val));
}
/**
* Pushes a long onto the top of this stack.
*
* @param val the value to push
*/
public void push(long val) {
this.push(new BaseTypeWrapper(val));
}
/**
* Pushes a short onto the top of this stack.
*
* @param val the value to push
*/
public void push(short val) {
this.push(new BaseTypeWrapper(val));
}
/**
* Pop an object.
*
* @return the object
*/
@Override
public Object pop() {
this.callStack.pop();
return super.pop();
}
/**
* Pop a boolean.
*
* @return the value
*/
public boolean popBoolean() {
BaseTypeWrapper wrapper = (BaseTypeWrapper) this.pop();
Boolean value = (Boolean) wrapper.getValue();
return value.booleanValue();
}
/**
* Pop a char.
*
* @return the value
*/
public char popChar() {
BaseTypeWrapper wrapper = (BaseTypeWrapper) this.pop();
Character value = (Character) wrapper.getValue();
return value.charValue();
}
/**
* Pop a double.
*
* @return the value
*/
public double popDouble() {
BaseTypeWrapper wrapper = (BaseTypeWrapper) this.pop();
Double value = (Double) wrapper.getValue();
return value.doubleValue();
}
/**
* Pop a float.
*
* @return the value
*/
public float popFloat() {
BaseTypeWrapper wrapper = (BaseTypeWrapper) this.pop();
Float value = (Float) wrapper.getValue();
return value.floatValue();
}
/**
* Pop a int.
*
* @return the value
*/
public int popInt() {
BaseTypeWrapper wrapper = (BaseTypeWrapper) this.pop();
Integer value = (Integer) wrapper.getValue();
return value.intValue();
}
/**
* Pop a long.
*
* @return the value
*/
public long popLong() {
BaseTypeWrapper wrapper = (BaseTypeWrapper) this.pop();
Long value = (Long) wrapper.getValue();
return value.longValue();
}
/**
* Pop a short.
*
* @return the value
*/
public short popShort() {
BaseTypeWrapper wrapper = (BaseTypeWrapper) this.pop();
Short value = (Short) wrapper.getValue();
return value.shortValue();
}
/*
* Wrapper of base types.
*/
class BaseTypeWrapper {
// the internal value
private Object value;
/*
* Constructs a wrapper object for the base type <code> boolean </code> .
*/
public BaseTypeWrapper(boolean val) {
this.value = new Boolean(val);
}
/*
* Constructs a wrapper object for the base type <code> c </code> .
*/
public BaseTypeWrapper(byte val) {
this.value = new Byte(val);
}
/*
* Constructs a wrapper object for the base type <code> char </code> .
*/
public BaseTypeWrapper(char val) {
this.value = new Character(val);
}
/*
* Constructs a wrapper object for the base type <code> double </code> .
*/
public BaseTypeWrapper(double val) {
this.value = new Double(val);
}
/*
* Constructs a wrapper object for the base type <code> float </code> .
*/
public BaseTypeWrapper(float val) {
this.value = new Float(val);
}
/*
* Constructs a wrapper object for the base type <code> int </code> .
*/
public BaseTypeWrapper(int val) {
this.value = new Integer(val);
}
/*
* Constructs a wrapper object for the base type <code> long </code> .
*/
public BaseTypeWrapper(long val) {
this.value = new Long(val);
}
/*
* Constructs a wrapper object for the base type <code> short </code> .
*/
public BaseTypeWrapper(short val) {
this.value = new Short(val);
}
/*
* Gets the internal value.
*/
public Object getValue() {
return this.value;
}
}
}