/*
 * Copyright (C) 2016 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.apksig.apk;

import com.android.apksig.internal.apk.AndroidBinXmlParser;
import com.android.apksig.internal.apk.stamp.SourceStampConstants;
import com.android.apksig.internal.apk.v1.V1SchemeVerifier;
import com.android.apksig.internal.util.Pair;
import com.android.apksig.internal.zip.CentralDirectoryRecord;
import com.android.apksig.internal.zip.LocalFileRecord;
import com.android.apksig.internal.zip.ZipUtils;
import com.android.apksig.util.DataSource;
import com.android.apksig.zip.ZipFormatException;

import java.io.IOException;
import java.nio.ByteBuffer;
import java.nio.ByteOrder;
import java.util.Arrays;
import java.util.Comparator;
import java.util.List;

/**
 * APK utilities.
 */
public abstract class ApkUtils {

    /**
     * Name of the Android manifest ZIP entry in APKs.
     */
    public static final String ANDROID_MANIFEST_ZIP_ENTRY_NAME = "AndroidManifest.xml";

    /** Name of the SourceStamp certificate hash ZIP entry in APKs. */
    public static final String SOURCE_STAMP_CERTIFICATE_HASH_ZIP_ENTRY_NAME =
            SourceStampConstants.SOURCE_STAMP_CERTIFICATE_HASH_ZIP_ENTRY_NAME;

    private ApkUtils() {}

    /**
     * Finds the main ZIP sections of the provided APK.
     *
     * @throws IOException if an I/O error occurred while reading the APK
     * @throws ZipFormatException if the APK is malformed
     */
    public static ZipSections findZipSections(DataSource apk)
            throws IOException, ZipFormatException {
        com.android.apksig.zip.ZipSections zipSections = ApkUtilsLite.findZipSections(apk);
        return new ZipSections(
                zipSections.getZipCentralDirectoryOffset(),
                zipSections.getZipCentralDirectorySizeBytes(),
                zipSections.getZipCentralDirectoryRecordCount(),
                zipSections.getZipEndOfCentralDirectoryOffset(),
                zipSections.getZipEndOfCentralDirectory());
    }

    /**
     * Information about the ZIP sections of an APK.
     */
    public static class ZipSections extends com.android.apksig.zip.ZipSections {
        public ZipSections(
                long centralDirectoryOffset,
                long centralDirectorySizeBytes,
                int centralDirectoryRecordCount,
                long eocdOffset,
                ByteBuffer eocd) {
            super(centralDirectoryOffset, centralDirectorySizeBytes, centralDirectoryRecordCount,
                    eocdOffset, eocd);
        }
    }

    /**
     * Sets the offset of the start of the ZIP Central Directory in the APK's ZIP End of Central
     * Directory record.
     *
     * @param zipEndOfCentralDirectory APK's ZIP End of Central Directory record
     * @param offset offset of the ZIP Central Directory relative to the start of the archive. Must
     *        be between {@code 0} and {@code 2^32 - 1} inclusive.
     */
    public static void setZipEocdCentralDirectoryOffset(
            ByteBuffer zipEndOfCentralDirectory, long offset) {
        ByteBuffer eocd = zipEndOfCentralDirectory.slice();
        eocd.order(ByteOrder.LITTLE_ENDIAN);
        ZipUtils.setZipEocdCentralDirectoryOffset(eocd, offset);
    }

    /**
     * Returns the APK Signing Block of the provided {@code apk}.
     *
     * @throws ApkFormatException if the APK is not a valid ZIP archive
     * @throws IOException if an I/O error occurs
     * @throws ApkSigningBlockNotFoundException if there is no APK Signing Block in the APK
     *
     * @see <a href="https://source.android.com/security/apksigning/v2.html">APK Signature Scheme v2
     * </a>
     */
    public static ApkSigningBlock findApkSigningBlock(DataSource apk)
            throws ApkFormatException, IOException, ApkSigningBlockNotFoundException {
        ApkUtils.ZipSections inputZipSections;
        try {
            inputZipSections = ApkUtils.findZipSections(apk);
        } catch (ZipFormatException e) {
            throw new ApkFormatException("Malformed APK: not a ZIP archive", e);
        }
        return findApkSigningBlock(apk, inputZipSections);
    }

    /**
     * Returns the APK Signing Block of the provided APK.
     *
     * @throws IOException if an I/O error occurs
     * @throws ApkSigningBlockNotFoundException if there is no APK Signing Block in the APK
     *
     * @see <a href="https://source.android.com/security/apksigning/v2.html">APK Signature Scheme v2
     * </a>
     */
    public static ApkSigningBlock findApkSigningBlock(DataSource apk, ZipSections zipSections)
            throws IOException, ApkSigningBlockNotFoundException {
        ApkUtilsLite.ApkSigningBlock apkSigningBlock = ApkUtilsLite.findApkSigningBlock(apk,
                zipSections);
        return new ApkSigningBlock(apkSigningBlock.getStartOffset(), apkSigningBlock.getContents());
    }

    /**
     * Information about the location of the APK Signing Block inside an APK.
     */
    public static class ApkSigningBlock extends ApkUtilsLite.ApkSigningBlock {
        /**
         * Constructs a new {@code ApkSigningBlock}.
         *
         * @param startOffsetInApk start offset (in bytes, relative to start of file) of the APK
         *        Signing Block inside the APK file
         * @param contents contents of the APK Signing Block
         */
        public ApkSigningBlock(long startOffsetInApk, DataSource contents) {
            super(startOffsetInApk, contents);
        }
    }

    /**
     * Returns the contents of the APK's {@code AndroidManifest.xml}.
     *
     * @throws IOException if an I/O error occurs while reading the APK
     * @throws ApkFormatException if the APK is malformed
     */
    public static ByteBuffer getAndroidManifest(DataSource apk)
            throws IOException, ApkFormatException {
        ZipSections zipSections;
        try {
            zipSections = findZipSections(apk);
        } catch (ZipFormatException e) {
            throw new ApkFormatException("Not a valid ZIP archive", e);
        }
        List<CentralDirectoryRecord> cdRecords =
                V1SchemeVerifier.parseZipCentralDirectory(apk, zipSections);
        CentralDirectoryRecord androidManifestCdRecord = null;
        for (CentralDirectoryRecord cdRecord : cdRecords) {
            if (ANDROID_MANIFEST_ZIP_ENTRY_NAME.equals(cdRecord.getName())) {
                androidManifestCdRecord = cdRecord;
                break;
            }
        }
        if (androidManifestCdRecord == null) {
            throw new ApkFormatException("Missing " + ANDROID_MANIFEST_ZIP_ENTRY_NAME);
        }
        DataSource lfhSection = apk.slice(0, zipSections.getZipCentralDirectoryOffset());

        try {
            return ByteBuffer.wrap(
                    LocalFileRecord.getUncompressedData(
                            lfhSection, androidManifestCdRecord, lfhSection.size()));
        } catch (ZipFormatException e) {
            throw new ApkFormatException("Failed to read " + ANDROID_MANIFEST_ZIP_ENTRY_NAME, e);
        }
    }

    /**
     * Android resource ID of the {@code android:minSdkVersion} attribute in AndroidManifest.xml.
     */
    private static final int MIN_SDK_VERSION_ATTR_ID = 0x0101020c;

    /**
     * Android resource ID of the {@code android:debuggable} attribute in AndroidManifest.xml.
     */
    private static final int DEBUGGABLE_ATTR_ID = 0x0101000f;

    /**
     * Android resource ID of the {@code android:targetSandboxVersion} attribute in
     * AndroidManifest.xml.
     */
    private static final int TARGET_SANDBOX_VERSION_ATTR_ID = 0x0101054c;

    /**
     * Android resource ID of the {@code android:targetSdkVersion} attribute in
     * AndroidManifest.xml.
     */
    private static final int TARGET_SDK_VERSION_ATTR_ID = 0x01010270;
    private static final String USES_SDK_ELEMENT_TAG = "uses-sdk";

    /**
     * Android resource ID of the {@code android:versionCode} attribute in AndroidManifest.xml.
     */
    private static final int VERSION_CODE_ATTR_ID = 0x0101021b;
    private static final String MANIFEST_ELEMENT_TAG = "manifest";

    /**
     * Android resource ID of the {@code android:versionCodeMajor} attribute in AndroidManifest.xml.
     */
    private static final int VERSION_CODE_MAJOR_ATTR_ID = 0x01010576;

    /**
     * Returns the lowest Android platform version (API Level) supported by an APK with the
     * provided {@code AndroidManifest.xml}.
     *
     * @param androidManifestContents contents of {@code AndroidManifest.xml} in binary Android
     *        resource format
     *
     * @throws MinSdkVersionException if an error occurred while determining the API Level
     */
    public static int getMinSdkVersionFromBinaryAndroidManifest(
            ByteBuffer androidManifestContents) throws MinSdkVersionException {
        // IMPLEMENTATION NOTE: Minimum supported Android platform version number is declared using
        // uses-sdk elements which are children of the top-level manifest element. uses-sdk element
        // declares the minimum supported platform version using the android:minSdkVersion attribute
        // whose default value is 1.
        // For each encountered uses-sdk element, the Android runtime checks that its minSdkVersion
        // is not higher than the runtime's API Level and rejects APKs if it is higher. Thus, the
        // effective minSdkVersion value is the maximum over the encountered minSdkVersion values.

        try {
            // If no uses-sdk elements are encountered, Android accepts the APK. We treat this
            // scenario as though the minimum supported API Level is 1.
            int result = 1;

            AndroidBinXmlParser parser = new AndroidBinXmlParser(androidManifestContents);
            int eventType = parser.getEventType();
            while (eventType != AndroidBinXmlParser.EVENT_END_DOCUMENT) {
                if ((eventType == AndroidBinXmlParser.EVENT_START_ELEMENT)
                        && (parser.getDepth() == 2)
                        && ("uses-sdk".equals(parser.getName()))
                        && (parser.getNamespace().isEmpty())) {
                    // In each uses-sdk element, minSdkVersion defaults to 1
                    int minSdkVersion = 1;
                    for (int i = 0; i < parser.getAttributeCount(); i++) {
                        if (parser.getAttributeNameResourceId(i) == MIN_SDK_VERSION_ATTR_ID) {
                            int valueType = parser.getAttributeValueType(i);
                            switch (valueType) {
                                case AndroidBinXmlParser.VALUE_TYPE_INT:
                                    minSdkVersion = parser.getAttributeIntValue(i);
                                    break;
                                case AndroidBinXmlParser.VALUE_TYPE_STRING:
                                    minSdkVersion =
                                            getMinSdkVersionForCodename(
                                                    parser.getAttributeStringValue(i));
                                    break;
                                default:
                                    throw new MinSdkVersionException(
                                            "Unable to determine APK's minimum supported Android"
                                                    + ": unsupported value type in "
                                                    + ANDROID_MANIFEST_ZIP_ENTRY_NAME + "'s"
                                                    + " minSdkVersion"
                                                    + ". Only integer values supported.");
                            }
                            break;
                        }
                    }
                    result = Math.max(result, minSdkVersion);
                }
                eventType = parser.next();
            }

            return result;
        } catch (AndroidBinXmlParser.XmlParserException e) {
            throw new MinSdkVersionException(
                    "Unable to determine APK's minimum supported Android platform version"
                            + ": malformed binary resource: " + ANDROID_MANIFEST_ZIP_ENTRY_NAME,
                    e);
        }
    }

    private static class CodenamesLazyInitializer {

        /**
         * List of platform codename (first letter of) to API Level mappings. The list must be
         * sorted by the first letter. For codenames not in the list, the assumption is that the API
         * Level is incremented by one for every increase in the codename's first letter.
         */
        @SuppressWarnings({"rawtypes", "unchecked"})
        private static final Pair<Character, Integer>[] SORTED_CODENAMES_FIRST_CHAR_TO_API_LEVEL =
                new Pair[] {
            Pair.of('C', 2),
            Pair.of('D', 3),
            Pair.of('E', 4),
            Pair.of('F', 7),
            Pair.of('G', 8),
            Pair.of('H', 10),
            Pair.of('I', 13),
            Pair.of('J', 15),
            Pair.of('K', 18),
            Pair.of('L', 20),
            Pair.of('M', 22),
            Pair.of('N', 23),
            Pair.of('O', 25),
        };

        private static final Comparator<Pair<Character, Integer>> CODENAME_FIRST_CHAR_COMPARATOR =
                new ByFirstComparator();

        private static class ByFirstComparator implements Comparator<Pair<Character, Integer>> {
            @Override
            public int compare(Pair<Character, Integer> o1, Pair<Character, Integer> o2) {
                char c1 = o1.getFirst();
                char c2 = o2.getFirst();
                return c1 - c2;
            }
        }
    }

    /**
     * Returns the API Level corresponding to the provided platform codename.
     *
     * <p>This method is pessimistic. It returns a value one lower than the API Level with which the
     * platform is actually released (e.g., 23 for N which was released as API Level 24). This is
     * because new features which first appear in an API Level are not available in the early days
     * of that platform version's existence, when the platform only has a codename. Moreover, this
     * method currently doesn't differentiate between initial and MR releases, meaning API Level
     * returned for MR releases may be more than one lower than the API Level with which the
     * platform version is actually released.
     *
     * @throws CodenameMinSdkVersionException if the {@code codename} is not supported
     */
    static int getMinSdkVersionForCodename(String codename) throws CodenameMinSdkVersionException {
        char firstChar = codename.isEmpty() ? ' ' : codename.charAt(0);
        // Codenames are case-sensitive. Only codenames starting with A-Z are supported for now.
        // We only look at the first letter of the codename as this is the most important letter.
        if ((firstChar >= 'A') && (firstChar <= 'Z')) {
            Pair<Character, Integer>[] sortedCodenamesFirstCharToApiLevel =
                    CodenamesLazyInitializer.SORTED_CODENAMES_FIRST_CHAR_TO_API_LEVEL;
            int searchResult =
                    Arrays.binarySearch(
                            sortedCodenamesFirstCharToApiLevel,
                            Pair.of(firstChar, null), // second element of the pair is ignored here
                            CodenamesLazyInitializer.CODENAME_FIRST_CHAR_COMPARATOR);
            if (searchResult >= 0) {
                // Exact match -- searchResult is the index of the matching element
                return sortedCodenamesFirstCharToApiLevel[searchResult].getSecond();
            }
            // Not an exact match -- searchResult is negative and is -(insertion index) - 1.
            // The element at insertionIndex - 1 (if present) is smaller than firstChar and the
            // element at insertionIndex (if present) is greater than firstChar.
            int insertionIndex = -1 - searchResult; // insertionIndex is in [0; array length]
            if (insertionIndex == 0) {
                // 'A' or 'B' -- never released to public
                return 1;
            } else {
                // The element at insertionIndex - 1 is the newest older codename.
                // API Level bumped by at least 1 for every change in the first letter of codename
                Pair<Character, Integer> newestOlderCodenameMapping =
                        sortedCodenamesFirstCharToApiLevel[insertionIndex - 1];
                char newestOlderCodenameFirstChar = newestOlderCodenameMapping.getFirst();
                int newestOlderCodenameApiLevel = newestOlderCodenameMapping.getSecond();
                return newestOlderCodenameApiLevel + (firstChar - newestOlderCodenameFirstChar);
            }
        }

        throw new CodenameMinSdkVersionException(
                "Unable to determine APK's minimum supported Android platform version"
                        + " : Unsupported codename in " + ANDROID_MANIFEST_ZIP_ENTRY_NAME
                        + "'s minSdkVersion: \"" + codename + "\"",
                codename);
    }

    /**
     * Returns {@code true} if the APK is debuggable according to its {@code AndroidManifest.xml}.
     * See the {@code android:debuggable} attribute of the {@code application} element.
     *
     * @param androidManifestContents contents of {@code AndroidManifest.xml} in binary Android
     *        resource format
     *
     * @throws ApkFormatException if the manifest is malformed
     */
    public static boolean getDebuggableFromBinaryAndroidManifest(
            ByteBuffer androidManifestContents) throws ApkFormatException {
        // IMPLEMENTATION NOTE: Whether the package is debuggable is declared using the first
        // "application" element which is a child of the top-level manifest element. The debuggable
        // attribute of this application element is coerced to a boolean value. If there is no
        // application element or if it doesn't declare the debuggable attribute, the package is
        // considered not debuggable.

        try {
            AndroidBinXmlParser parser = new AndroidBinXmlParser(androidManifestContents);
            int eventType = parser.getEventType();
            while (eventType != AndroidBinXmlParser.EVENT_END_DOCUMENT) {
                if ((eventType == AndroidBinXmlParser.EVENT_START_ELEMENT)
                        && (parser.getDepth() == 2)
                        && ("application".equals(parser.getName()))
                        && (parser.getNamespace().isEmpty())) {
                    for (int i = 0; i < parser.getAttributeCount(); i++) {
                        if (parser.getAttributeNameResourceId(i) == DEBUGGABLE_ATTR_ID) {
                            int valueType = parser.getAttributeValueType(i);
                            switch (valueType) {
                                case AndroidBinXmlParser.VALUE_TYPE_BOOLEAN:
                                case AndroidBinXmlParser.VALUE_TYPE_STRING:
                                case AndroidBinXmlParser.VALUE_TYPE_INT:
                                    String value = parser.getAttributeStringValue(i);
                                    return ("true".equals(value))
                                            || ("TRUE".equals(value))
                                            || ("1".equals(value));
                                case AndroidBinXmlParser.VALUE_TYPE_REFERENCE:
                                    // References to resources are not supported on purpose. The
                                    // reason is that the resolved value depends on the resource
                                    // configuration (e.g, MNC/MCC, locale, screen density) used
                                    // at resolution time. As a result, the same APK may appear as
                                    // debuggable in one situation and as non-debuggable in another
                                    // situation. Such APKs may put users at risk.
                                    throw new ApkFormatException(
                                            "Unable to determine whether APK is debuggable"
                                                    + ": " + ANDROID_MANIFEST_ZIP_ENTRY_NAME + "'s"
                                                    + " android:debuggable attribute references a"
                                                    + " resource. References are not supported for"
                                                    + " security reasons. Only constant boolean,"
                                                    + " string and int values are supported.");
                                default:
                                    throw new ApkFormatException(
                                            "Unable to determine whether APK is debuggable"
                                                    + ": " + ANDROID_MANIFEST_ZIP_ENTRY_NAME + "'s"
                                                    + " android:debuggable attribute uses"
                                                    + " unsupported value type. Only boolean,"
                                                    + " string and int values are supported.");
                            }
                        }
                    }
                    // This application element does not declare the debuggable attribute
                    return false;
                }
                eventType = parser.next();
            }

            // No application element found
            return false;
        } catch (AndroidBinXmlParser.XmlParserException e) {
            throw new ApkFormatException(
                    "Unable to determine whether APK is debuggable: malformed binary resource: "
                            + ANDROID_MANIFEST_ZIP_ENTRY_NAME,
                    e);
        }
    }

    /**
     * Returns the package name of the APK according to its {@code AndroidManifest.xml} or
     * {@code null} if package name is not declared. See the {@code package} attribute of the
     * {@code manifest} element.
     *
     * @param androidManifestContents contents of {@code AndroidManifest.xml} in binary Android
     *        resource format
     *
     * @throws ApkFormatException if the manifest is malformed
     */
    public static String getPackageNameFromBinaryAndroidManifest(
            ByteBuffer androidManifestContents) throws ApkFormatException {
        // IMPLEMENTATION NOTE: Package name is declared as the "package" attribute of the top-level
        // manifest element. Interestingly, as opposed to most other attributes, Android Package
        // Manager looks up this attribute by its name rather than by its resource ID.

        try {
            AndroidBinXmlParser parser = new AndroidBinXmlParser(androidManifestContents);
            int eventType = parser.getEventType();
            while (eventType != AndroidBinXmlParser.EVENT_END_DOCUMENT) {
                if ((eventType == AndroidBinXmlParser.EVENT_START_ELEMENT)
                        && (parser.getDepth() == 1)
                        && ("manifest".equals(parser.getName()))
                        && (parser.getNamespace().isEmpty())) {
                    for (int i = 0; i < parser.getAttributeCount(); i++) {
                        if ("package".equals(parser.getAttributeName(i))
                                && (parser.getNamespace().isEmpty())) {
                            return parser.getAttributeStringValue(i);
                        }
                    }
                    // No "package" attribute found
                    return null;
                }
                eventType = parser.next();
            }

            // No manifest element found
            return null;
        } catch (AndroidBinXmlParser.XmlParserException e) {
            throw new ApkFormatException(
                    "Unable to determine APK package name: malformed binary resource: "
                            + ANDROID_MANIFEST_ZIP_ENTRY_NAME,
                    e);
        }
    }

    /**
     * Returns the security sandbox version targeted by an APK with the provided
     * {@code AndroidManifest.xml}.
     *
     * <p>If the security sandbox version is not specified in the manifest a default value of 1 is
     * returned.
     *
     * @param androidManifestContents contents of {@code AndroidManifest.xml} in binary Android
     *                                resource format
     */
    public static int getTargetSandboxVersionFromBinaryAndroidManifest(
            ByteBuffer androidManifestContents) {
        try {
            return getAttributeValueFromBinaryAndroidManifest(androidManifestContents,
                    MANIFEST_ELEMENT_TAG, TARGET_SANDBOX_VERSION_ATTR_ID);
        } catch (ApkFormatException e) {
            // An ApkFormatException indicates the target sandbox is not specified in the manifest;
            // return a default value of 1.
            return 1;
        }
    }

    /**
     * Returns the SDK version targeted by an APK with the provided {@code AndroidManifest.xml}.
     *
     * <p>If the targetSdkVersion is not specified the minimumSdkVersion is returned. If neither
     * value is specified then a value of 1 is returned.
     *
     * @param androidManifestContents contents of {@code AndroidManifest.xml} in binary Android
     *                                resource format
     */
    public static int getTargetSdkVersionFromBinaryAndroidManifest(
            ByteBuffer androidManifestContents) {
        // If the targetSdkVersion is not specified then the platform will use the value of the
        // minSdkVersion; if neither is specified then the platform will use a value of 1.
        int minSdkVersion = 1;
        try {
            return getAttributeValueFromBinaryAndroidManifest(androidManifestContents,
                    USES_SDK_ELEMENT_TAG, TARGET_SDK_VERSION_ATTR_ID);
        } catch (ApkFormatException e) {
            // Expected if the APK does not contain a targetSdkVersion attribute or the uses-sdk
            // element is not specified at all.
        }
        androidManifestContents.rewind();
        try {
            minSdkVersion = getMinSdkVersionFromBinaryAndroidManifest(androidManifestContents);
        } catch (ApkFormatException e) {
            // Similar to above, expected if the APK does not contain a minSdkVersion attribute, or
            // the uses-sdk element is not specified at all.
        }
        return minSdkVersion;
    }

    /**
     * Returns the versionCode of the APK according to its {@code AndroidManifest.xml}.
     *
     * <p>If the versionCode is not specified in the {@code AndroidManifest.xml} or is not a valid
     * integer an ApkFormatException is thrown.
     *
     * @param androidManifestContents contents of {@code AndroidManifest.xml} in binary Android
     *                                resource format
     * @throws ApkFormatException if an error occurred while determining the versionCode, or if the
     *                            versionCode attribute value is not available.
     */
    public static int getVersionCodeFromBinaryAndroidManifest(ByteBuffer androidManifestContents)
            throws ApkFormatException {
        return getAttributeValueFromBinaryAndroidManifest(androidManifestContents,
                MANIFEST_ELEMENT_TAG, VERSION_CODE_ATTR_ID);
    }

    /**
     * Returns the versionCode and versionCodeMajor of the APK according to its {@code
     * AndroidManifest.xml} combined together as a single long value.
     *
     * <p>The versionCodeMajor is placed in the upper 32 bits, and the versionCode is in the lower
     * 32 bits. If the versionCodeMajor is not specified then the versionCode is returned.
     *
     * @param androidManifestContents contents of {@code AndroidManifest.xml} in binary Android
     *                                resource format
     * @throws ApkFormatException if an error occurred while determining the version, or if the
     *                            versionCode attribute value is not available.
     */
    public static long getLongVersionCodeFromBinaryAndroidManifest(
            ByteBuffer androidManifestContents) throws ApkFormatException {
        // If the versionCode is not found then allow the ApkFormatException to be thrown to notify
        // the caller that the versionCode is not available.
        int versionCode = getVersionCodeFromBinaryAndroidManifest(androidManifestContents);
        long versionCodeMajor = 0;
        try {
            androidManifestContents.rewind();
            versionCodeMajor = getAttributeValueFromBinaryAndroidManifest(androidManifestContents,
                    MANIFEST_ELEMENT_TAG, VERSION_CODE_MAJOR_ATTR_ID);
        } catch (ApkFormatException e) {
            // This is expected if the versionCodeMajor has not been defined for the APK; in this
            // case the return value is just the versionCode.
        }
        return (versionCodeMajor << 32) | versionCode;
    }

    /**
     * Returns the integer value of the requested {@code attributeId} in the specified {@code
     * elementName} from the provided {@code androidManifestContents} in binary Android resource
     * format.
     *
     * @throws ApkFormatException if an error occurred while attempting to obtain the attribute, or
     *                            if the requested attribute is not found.
     */
    private static int getAttributeValueFromBinaryAndroidManifest(
            ByteBuffer androidManifestContents, String elementName, int attributeId)
            throws ApkFormatException {
        if (elementName == null) {
            throw new NullPointerException("elementName cannot be null");
        }
        try {
            AndroidBinXmlParser parser = new AndroidBinXmlParser(androidManifestContents);
            int eventType = parser.getEventType();
            while (eventType != AndroidBinXmlParser.EVENT_END_DOCUMENT) {
                if ((eventType == AndroidBinXmlParser.EVENT_START_ELEMENT)
                        && (elementName.equals(parser.getName()))) {
                    for (int i = 0; i < parser.getAttributeCount(); i++) {
                        if (parser.getAttributeNameResourceId(i) == attributeId) {
                            int valueType = parser.getAttributeValueType(i);
                            switch (valueType) {
                                case AndroidBinXmlParser.VALUE_TYPE_INT:
                                case AndroidBinXmlParser.VALUE_TYPE_STRING:
                                    return parser.getAttributeIntValue(i);
                                default:
                                    throw new ApkFormatException(
                                            "Unsupported value type, " + valueType
                                                    + ", for attribute " + String.format("0x%08X",
                                                    attributeId) + " under element " + elementName);

                            }
                        }
                    }
                }
                eventType = parser.next();
            }
            throw new ApkFormatException(
                    "Failed to determine APK's " + elementName + " attribute "
                            + String.format("0x%08X", attributeId) + " value");
        } catch (AndroidBinXmlParser.XmlParserException e) {
            throw new ApkFormatException(
                    "Unable to determine value for attribute " + String.format("0x%08X",
                            attributeId) + " under element " + elementName
                            + "; malformed binary resource: " + ANDROID_MANIFEST_ZIP_ENTRY_NAME, e);
        }
    }

    public static byte[] computeSha256DigestBytes(byte[] data) {
        return ApkUtilsLite.computeSha256DigestBytes(data);
    }
}
