blob: a962af51fba20d5b5b33e457ba49c7ec30bf9e16 [file] [log] [blame]
/*
* Copyright (C) 2008 The Android Open Source Project
*
* 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 com.android.apicheck;
public class FieldInfo {
private String mName;
private String mType;
private boolean mIsTransient;
private boolean mIsVolatile;
private String mValue;
private boolean mIsStatic;
private boolean mIsFinal;
private String mDeprecated;
private String mScope;
private boolean mExistsInBoth;
private SourcePositionInfo mSourcePosition;
private ClassInfo mClass;
public FieldInfo (String name, String type, boolean isTransient, boolean isVolatile,
String value, boolean isStatic, boolean isFinal, String deprecated,
String scope, SourcePositionInfo source, ClassInfo parent) {
mName = name;
mType = type;
mIsTransient = isTransient;
mIsVolatile = isVolatile;
mValue = value;
mIsStatic = isStatic;
mIsFinal = isFinal;
mDeprecated = deprecated;
mScope = scope;
mExistsInBoth = false;
mSourcePosition = source;
mClass = parent;
}
public boolean isInBoth() {
return mExistsInBoth;
}
public SourcePositionInfo position() {
return mSourcePosition;
}
public String name() {
return mName;
}
public String qualifiedName() {
String parentQName = (mClass != null)
? (mClass.qualifiedName() + ".")
: "";
return parentQName + name();
}
// Check the declared value with a typed comparison, not a string comparison,
// to accommodate toolchains with different fp -> string conversions.
public boolean valueEquals(FieldInfo other) {
// Type mismatch means nonequal, as does a null/non-null mismatch
if (!mType.equals(other.mType)
|| ((mValue == null) != (other.mValue == null))) {
return false;
}
// Null values are considered equal
if (mValue == null) {
return true;
}
// Floating point gets an implementation-type comparison; all others just use the string
// If float/double parse fails, fall back to string comparison -- it means that it's a
// canonical droiddoc-generated constant expression that represents a NaN.
try {
if (mType.equals("float")) {
float val = Float.parseFloat(mValue);
float otherVal = Float.parseFloat(other.mValue);
return (val == otherVal);
} else if (mType.equals("double")) {
double val = Double.parseDouble(mValue);
double otherVal = Double.parseDouble(other.mValue);
return (val == otherVal);
}
} catch (NumberFormatException e) {
// fall through
}
return mValue.equals(other.mValue);
}
public boolean isConsistent(FieldInfo fInfo) {
fInfo.mExistsInBoth = true;
mExistsInBoth = true;
boolean consistent = true;
if (!mType.equals(fInfo.mType)) {
Errors.error(Errors.CHANGED_TYPE, fInfo.position(),
"Field " + fInfo.qualifiedName() + " has changed type");
consistent = false;
}
if (!this.valueEquals(fInfo)) {
Errors.error(Errors.CHANGED_VALUE, fInfo.position(),
"Field " + fInfo.qualifiedName() + " has changed value from "
+ mValue + " to " + fInfo.mValue);
consistent = false;
}
if (!mScope.equals(fInfo.mScope)) {
Errors.error(Errors.CHANGED_SCOPE, fInfo.position(),
"Method " + fInfo.qualifiedName() + " changed scope from "
+ mScope + " to " + fInfo.mScope);
consistent = false;
}
if (mIsStatic != fInfo.mIsStatic) {
Errors.error(Errors.CHANGED_STATIC, fInfo.position(),
"Field " + fInfo.qualifiedName() + " has changed 'static' qualifier");
consistent = false;
}
if (mIsFinal != fInfo.mIsFinal) {
Errors.error(Errors.CHANGED_FINAL, fInfo.position(),
"Field " + fInfo.qualifiedName() + " has changed 'final' qualifier");
consistent = false;
}
if (mIsTransient != fInfo.mIsTransient) {
Errors.error(Errors.CHANGED_TRANSIENT, fInfo.position(),
"Field " + fInfo.qualifiedName() + " has changed 'transient' qualifier");
consistent = false;
}
if (mIsVolatile != fInfo.mIsVolatile) {
Errors.error(Errors.CHANGED_VOLATILE, fInfo.position(),
"Field " + fInfo.qualifiedName() + " has changed 'volatile' qualifier");
consistent = false;
}
return consistent;
}
}