private boolean isEquivalent(Function function1, Function function2) {
		if (function1 == function2) {
			return true;
		}
		if (function1 == null || function2 == null) {
			return false;
		}

		if (!function1.getName().equals(function2.getName())) {
			return false;
		}
		if (function1.isExternal()) {
			if (!SystemUtilities.isEqual(function1.getExternalLocation(),
				function2.getExternalLocation())) {
				return false;
			}
		}
		else if (function2.isExternal()) {
			return false;
		}
		if (!function1.getEntryPoint().equals(function2.getEntryPoint())) {
			return false;
		}

		if (!SystemUtilities.isEqual(function1.getBody(), function2.getBody())) {
			return false;
		}

		Function thunkedFunction1 = function1.getThunkedFunction(false);
		Function thunkedFunction2 = function2.getThunkedFunction(false);
		if (thunkedFunction1 != null) {
			if (thunkedFunction2 == null) {
				return false;
			}
			if (thunkedFunction1.isExternal() != thunkedFunction2.isExternal()) {
				return false;
			}
			if (!thunkedFunction1.isExternal()) {
				return thunkedFunction1.getEntryPoint().equals(thunkedFunction2.getEntryPoint());
			}
			return isEquivalent(thunkedFunction1, thunkedFunction2);
		}
		else if (thunkedFunction2 != null) {
			return false;
		}

		// TODO: using isEquivelent seems bad

		Parameter returnParam1 = function1.getReturn();
		Parameter returnParam2 = function2.getReturn();
		if (!returnParam1.equals(returnParam2)) {
			return false;
		}

		if (function1.getStackPurgeSize() != function2.getStackPurgeSize()) {
			return false;
		}
		if (function1.getStackFrame().getReturnAddressOffset() != function2.getStackFrame()
				.getReturnAddressOffset()) {
			return false;
		}
		if (!function1.getCallingConventionName().equals(function2.getCallingConventionName())) {
			return false;
		}
		if (function1.hasVarArgs() != function2.hasVarArgs()) {
			return false;
		}
		if (function1.isInline() != function2.isInline()) {
			return false;
		}
		if (function1.hasNoReturn() != function2.hasNoReturn()) {
			return false;
		}
		if (function1.hasCustomVariableStorage() != function2.hasCustomVariableStorage()) {
			return false;
		}
		if (function1.getSignatureSource() != function2.getSignatureSource()) {
			return false;
		}

		if (!VariableUtilities.equivalentVariableArrays(function1.getParameters(),
			function2.getParameters())) {
			return false;
		}
		if (!VariableUtilities.equivalentVariableArrays(function1.getLocalVariables(),
			function2.getLocalVariables())) {
			return false;
		}
		return true;

	}
Updates the progress bar and the progress message details associated with this
phase of the merge.
@param myPercentComplete the progress percentage completed for this merger.
This should be a value from 0 to 100.
@param message a message indicating what is currently occurring in this phase.
Null indicates to use the default message.
Ghidra/Features/Base/src/main/java/ghidra/app/merge/listing/FunctionMerger.java